j.u.Objects follow-up: deepEquals(Object, Object)? (original) (raw)
Osvaldo Doederlein opinali at gmail.com
Fri Oct 9 12:50:23 UTC 2009
- Previous message: j.u.Objects follow-up: deepEquals(Object, Object)?
- Next message: Quick code review request for 634992 (enum) Include links from java.lang.Enum to EnumSet and EnumMap
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]
Hi,
Some suggestions:
Any equals*(a, b) methods should support a==null && b==null returning true, only a==null returning -1, and only b==null returning +1. This is very useful for much the same reasons that it's useful in SQL (although the exact ordering of null/non-null is debatable - SQL defaults to "nulls last" but allows you to specify NULLS FIRST, and I agree that its default "nulls first" makes more sense most of the time). This handling of nulls should also extend to any elements of a and b.
What the platform REALLY needs is a System.arrayequals(Object src1, int pos1, Object src2, int pos2, int length) that, just like the existing arraycopy(), handles arrays of arbitrary types (that's why src1/src2 are specified as Object). The implementation is trivial (with JNI): just compare the element types, do all the parameter/bound checking and if OK, call memcmp() with the addresses of src1[pos1] and src2[pos2], and length translated to bytes. A better implementation would perform intrinsic compilation. I think the various typed Arrays.equals(a,b) methods already do such optimization (the reason for documentation like: "Unlike the ==operator, this method considers NaN equals to itself, and 0.0d unequal to -0.0d."), but these still leave use with the cost of a long case analysis for scenarios like deepEquals() that must handle arrays of arbitrary element-types. IMHO all those typed equals(a,b) should just delegate to a single method, in the System class (not Arrays, not ObjectUtils or whatever), that provides a low-level "raw equals" function. With this low-level (but still safe) function, we can build higher-level APIs like a deepEquals(a,b) with optimum performance. Also, in the current platform there's ByteBuffer.equals() that supports comparison of buffers of arbitrary element types without case analysis, and I guess is also compiled as intrinsic; but I don't want to wrap all my arrays in NIO buffers. The ByteBuffer.equals() should also delegate to the unified System.arrayequals().
A+ Osvaldo
2009/10/8 Joseph D. Darcy <Joe.Darcy at sun.com>
Another piece of functionality requested in the j.u.Objects thread was a deepEquals(Object a, Object b.) method that "did the right thing" if the arguments happened to dynamically be arrays.
I've been thinking a bit how this might be implemented. The array-ness of a and b would need to be determined, after any up-front null-checks boolean aIsArray = a.getClass().isArray(); boolean bIsArray = b.getClass().isArray(); followed various case-analyses. if (aIsArray && bIsArray) { Class<?> aComponentType = a.getClass().getComponentType(); Class<?> bComponentType = b.getClass().getComponentType(); if (aComponentType == bComponentType) { // long case analysis to cast and call Arrays.deepEquals if ComponentType is a reference type // or the matching Arrays.equals(primitiveComponent[], primitiveComponent[]) method if // aComponentType.isPrimitive(). } else return false; } else return a.equals(b); Certainly a bit messy internally. What are scenarios where this method would be used? -Joe -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.openjdk.java.net/pipermail/core-libs-dev/attachments/20091009/0bb5265a/attachment.html>
- Previous message: j.u.Objects follow-up: deepEquals(Object, Object)?
- Next message: Quick code review request for 634992 (enum) Include links from java.lang.Enum to EnumSet and EnumMap
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]