Recursively comparing

Remi Forax forax at univ-mlv.fr
Tue Feb 27 15:07:13 UTC 2024


> From: "Pedro Lamarão" <pedro.lamarao at prodist.com.br>
> To: "valhalla-dev" <valhalla-dev at openjdk.org>
> Sent: Tuesday, February 27, 2024 3:49:00 PM
> Subject: Recursively comparing

> Hello all!

Hello, 

> In reviewing the latest edition of JEP 401, I came into language that made me a
> little confused.

> In section "Identity-sensitive operations" we read:

> "Fields with primitive types are compared by their bit patterns. Other field
> values—both identity and value objects—are recursively compared with ==."

> Later, we read:

> "Also note that the == operator does not perform a "deep equals" comparison on
> identity objects stored in fields (...)"

> My understanding of value classes so far has been that value objects are
> compared as-if by &&-ing the ==s of its fields. This seems to me the meaning of
> identity object fields not being compared by some deep equals algorithm.
> However, earlier, the text says that identity objects are recursively compared
> with ==. But recursively means to me something similar to deep: one would
> "recurse into" the object`s own fields.

> I am not a native english speaker. Am I reading this incorrectly? What is the
> intention of saying that other field values, including identity object fields,
> are recursively compared with ==?

I do not think the spec is not clear but let's take an example 
value record Foo(int i, float f) { } 

var foo1 = new Foo(); 
var foo2 = new Foo(); 

foo1 == foo2 
is equivalent to 
bitpattern(foo1.i) == bitpattern((foo2.i) && bitpattern(foo1.f) == bitpattern(foo2.f) 

All primitives are compared using their bitpattern, for an int, bitpattern is equivalent to ==, but for a float, bit pattern is Float. floatToRawIntBits (). 

Now, let say, there is a third component of type Object 
value record Foo(int i, float f, Object o) { } 

In that case, foo1 == foo2 
is equivalent to 
bitpattern(foo1.i) == bitpattern((foo2.i) && bitpattern(foo1.f) == bitpattern(foo2.f) && foo1.o == foo2.o 

So if 'o' is an identity object, like String, the address will be used and if 'o' is itself a value type, like Foo, then == becomes a recursive call. 

Is it more clear ? 

> --
> Pedro Lamarão

Rémi 
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://mail.openjdk.org/pipermail/valhalla-dev/attachments/20240227/9ffad8f9/attachment.htm>


More information about the valhalla-dev mailing list