Why doesn't Kotlin use better names for number types?

Kotlin uses number types with not self-explanatory names like Short, Int, Long, Float, Double. Today I stumbled over a discussion in which the questions “Double what?” and “Long what?” came up.

Kotlin decided to use other names than Java for number types, so the argument to use the same names as Java wouldn’t apply. But why are not more descriptive names used then?

In my opinion Rust has better names:

  • signed integers: i8 , i16 , i32 , i64 , i128
  • unsigned integers: u8 , u16 , u32 , u64 , u128
  • floating point: f32 , f64

My suggestion for Kotlin would be:

  • ByteInt8
  • ShortInt16
  • IntInt32
  • LongInt64
  • FloatFloat32
  • DoubleFloat64

Another advantage would be that other types like Int128 could be added easily and consistently.

Would it even be imaginable to deprecate such common names and to replace them with more descriptive ones in Kotlin?

3 Likes

I see the merit in how this change can help beginners, but also I think that having the number of bytes after the type is just kind of too noisy if you get what I mean. It carries more of a mental weight to think about “well this is an int16 but this is an int32”, while with the current names the thinking is more like “okay well when I immediately see Int I know this is just normal code and when I see Double or Float then it’s something division or graphics related and oh when I see Short or Long this is either high-performance code or some rather specific usecase” and it sort of highlights that the default is to use Ints and Doubles almost everywhere, which programmers who are familiar with that are very used to nowadays.

4 Likes

Pretty sure that the main reason is that they are named that way in Java. Since interoperability with Java is a very high priority in Kotlins design, it would be confusing if the same types had vastly different names between the two languages.

As for why they are named that way in Java, my guess is that it follows the tradition from C. In C, long and short are just shorthand aliases for long int and short int respectively. Just be glad that at least the ranges of the integer types are well-defined in Java and Kotlin, unlike in C.

7 Likes

What Kotlin really needs is a 53-bit integer type, and nobody would want to call it a Medium or Longish, so I think this scheme has merit :slight_smile:

8 Likes
typealias Float32 = Float

Solves all your problems without inventing new ones.

15 Likes

Don’t worry, non-believers of this one will feel the pain when Kotlin is forced to introduce the LongLong type in the future.

(Those of us who work in file formats where some data is not stored in convenient 8-bit blocks already feel this sort of pain because we wish we could have structs with things like Int1 or Int4 in them.)

2 Likes

I doubt Java or Kotlin would be forced to add something like longlong.

I prefer the current names as I think application programming it’s relatively practical, easy to learn (including what they mean), and they’re sane defaults. I understand if someone disagrees though.

Value classes (aka your own custom primatives) should fix this, no? If you want some crazy Int42 or Float7, you can make it yourself and get all the nice optimizations associated with value classes.

2 Likes

I work with file formats. If I need new types, I create them inside my program. It is that simple.

5 Likes

Kotlin did rename ObjectAny and voidUnit; FloatFloat32 doesn’t sound far-fetched.

However, I agree with Varia: names should be simple, and after you read the documentation of Float once, you’ll never have any questions about it.

Also, Kotlin is not an ultra-performance language, trying to use Short instead of Int will not, in most cases, speed up your program, so it’s better if beginners don’t think too much about it.

1 Like

Shorts are not always faster than Ints in C either. It depends greatly on the operations you are doing, how much cache is involved etc etc.

2 Likes

It is not an actual problem I have with these names, since I learned these types some 20 years ago. It was more a fundamental thought if the language could be improved here. So, as much as I like your idea with type aliases, it wouldn’t make it into any tutorial for beginners, because it would be even more confusing, if it wouldn’t be the standard name.

However, since most Kotlin folks would have some Java background, new names like Int64 might be confusing anyway.

On the floating point side the distinction comes from the IEEE 754 spec that defines the floating point representations of numbers. It defines single-precision floating point (which it calls binary32) and double-precision floating point (which it calls binary64). It also defines half-precision, quadruple-precision, and even octuple-precision. So the answer to Double what?, the answer is double the precision.

While it may have been more consistent to name these as Single and Double as was done in Delphi and Visual Basic, there is a long history of calling of these float and double that dates back at least 50 years to the C language.

Adding the number of bits for these is not really relevant as the primary concern is how precise the number is, not necessarily how man bits it takes up. The number of bits was more of a concern in early days of computing.

On the integral side Kotlin is following the 25-year old example of Java, which was a vast improvement on the old days of C/C++. In C and C++ how many bits an int or long int took up was platform specific. Int could be 16-bits, 32-bits, or 64 bits and long int could be 32-bits or 64-bits. It was not defined by the language, which lead to the need to define aliases like int32 to remove the ambigutity.

Java at least standardized on 2 primary integral types, long and int and fixed their size as 64 and 32 bits. I say they are the primary types because all math is done in either 32 or 64 bits. There are the short, char, and byte types (along with unsigned versions in Kotlin) that define smaller types but they are always promoted to 32 or 64 bits for any math. So the answer to Long what? is a Long Int. In C you could use long as an adjective like signed and unsigned and say long int but could shorten it to just long and that became the norm which Java and Kotlin both continued.

Since Kotlin was originally a better Java it made since to follow the same naming. If you don’t like those names you are free to use typealias to make your own names.

5 Likes

Actually, no. And that’s also the answer of why the names are like they are: they are copied over from Java for (mental) interoperability. I don’t know how you came to the conclusion that they changed the names, because

Java    -> Kotlin

boolean -> Boolean
byte    -> Byte
char    -> Char
short   -> Short
int     -> Int
long    -> Long
float   -> Float
double  -> Double

The only difference is that the names start with uppercase letters, which is a convention for non-primitives. Since Kotlin has no primitives (at use-site), this makes perfect sense.

You might have been confused by Javas boxed (non-primitive) numbers, like Integer. They are not the same as Kotlin pseudo-primitives, since those might represent an unboxed primitive at runtime based on the usage (non-nullable, not as generic, …).

  • Yes, Object became Any, although those two types are not considered the same in Kotlin/JVM.
  • void and Unit are fundamentally different. Unit in Kotlin was necessary to increase the languages’ expressiveness. It’s not a renaming, it’s a different thing. Naming that different thing Void as well would just lead to confusion.
2 Likes

Also, void is just wrong. The term void refers to the empty set, and it is mathematically incorrect to say a function’s type is void, because that function therefore cannot return. The real void type is named Nothing in Kotlin (I assume, because naming it void would confuse everyone, even if mathematically correct), and doesn’t exist in Java.