Reputation: 1482
bit mask 0xaaaaaaaaaaaaaaaaL
(16a's) is out or range in kotlin. If I have Android Sutdio automatically convert from Java, it translate to -0x5555555555555556L
, which is 101010101010101010101010101010101010101010101010101010101010110
, it is now only 63 bit and 0110 at the end is off.
0xaaaaaaaaaaaaaaaaL
works well in Java. I need an explanation of why it becomes -0x5555555555555556L
in kotlin.
Another question is how does kotlin represent negative Long? Why the - sign in the front? It is not 2's complement like in Java?
I looked at the doc https://kotlinlang.org/docs/basic-types.html#literal-constants, I know kotlin support Hexadecimals syntax.
I also tried Unsigned Long val mask2: ULong = 0xaaaaaaaaaaaaaaaaL
same problem.
Thanks in advance
Upvotes: 5
Views: 3994
Reputation: 23147
Kotlin doesn't let you create literal values greater than Long.MAX_VALUE
, but you can declare an unsigned long and convert it to a long with he same binary value like this:
val long = 0xaaaaaaaaaaaaaaaau.toLong()
Example:
fun main() {
val long = 0xaaaaaaaaaaaaaaaau.toLong()
println(long.toString(16))
println(long.toString(2))
println(long.toULong().toString(16))
println(long.toULong().toString(2))
}
Output:
-5555555555555556
-101010101010101010101010101010101010101010101010101010101010110
aaaaaaaaaaaaaaaa
1010101010101010101010101010101010101010101010101010101010101010
Upvotes: 4
Reputation: 275015
The reason why that literal works in Java is because Java's hexadecimal integer literals can represent negative numbers, and 0xaaaaaaaaaaaaaaaaL
just so happens to fit 64 bits. From the JLS 3.10.1:
A hexadecimal numeral consists of the leading ASCII characters 0x or 0X followed by one or more ASCII hexadecimal digits interspersed with underscores, and can represent a positive, zero, or negative integer.
It is a compile-time error if a hexadecimal, octal, or binary long literal does not fit in 64 bits.
(Note that decimal literals in Java OTOH can only represent non-negative integers).
So in Java, 0xaaaaaaaaaaaaaaaaL
doesn't represent the positive number
12297829382473034410
After all, Long
in both languages only has the max value of
9223372036854775807
It instead represents the negative number
-6148914691236517206
You can see that this is the case in Java by printing the number in hex:
long a = 0xaaaaaaaaaaaaaaaaL;
System.out.println(Long.toString(a, 16));
// -5555555555555556
// this is the same hex you get when you translate to Kotlin!
Kotlin's hexadecimal literals don't represent negative integers, so 0xaaaaaaaaaaaaaaaaL
is out of range, because it represents 12297829382473034410, rather than -6148914691236517206.
Upvotes: 3