Why isn't my JVM Double variable the same as itself in 1.6.10?
Copy code
val dotOne: Double = "0.1".toDouble()
assertSame(dotOne, dotOne)
expected: java.lang.Double@76774d21<0.1> but was: java.lang.Double@68be905c<0.1>
I understand that
assertSame
uses referential equality (checks that the parameters have the same virtual memory address) and should function like the
===
operator.
0.1 !== 0.1
because they are primitives and could be boxed to different objects before being compared for referential equality. But, when I declare a variable, I would expect it to have the same virtual memory address as itself. Be referentially (and structurally) equivalent to itself.
Can I declare my variable somehow to not be compiled away to two different primitives that happen to have different virtual memory addresses?
e
ephemient
01/03/2022, 10:44 PM
no, because the primitive 1.6 does not have a memory address. every time it is boxed, a new object is created.
🙏🏻 1
🙏 2
g
glenkpeterson
01/03/2022, 10:46 PM
So this will be an issue with any boxed primitive type and should work as I expected with any unboxed type?
e
ephemient
01/03/2022, 10:47 PM
the same does not apply to small ints and longs as the JVM keeps a small cache of fixed instances, but it does for large ints and longs, as well as floats and doubles
as described in the article, LongCache is not tunable, and neither are the
Boolean.TRUE
and
Boolean.FALSE
static instances
🙏🏻 1
g
glenkpeterson
01/03/2022, 10:55 PM
Yay: small cache of fixed instances.
But... why is Kotlin boxing and unboxing a variable that's only used when it's boxed? Isn't that wasteful?
Also, from your article I learned that I can make it nullable to force a boxed variable, which answers the end of my original question: