Hi Neil,
Neil Richards said the following on 07/20/11 20:51:
java.lang.invoke.MethodHandleProxies.isSingleMethod(Class<?> intf)
returns a boolean indicating whether the provided interface has only one
defined method upon it.
When making this consideration, it tries not count any method defined on
the interface that is also defined by java.lang.Object (and so will
always be there for all implementations of the interface).
Because of this, for example, isSingleMethod should return 'true' for
java.util.Comparator, which has two defined methods - compare() and
equals() - as all but one of these methods are also defined by
java.lang.Object.
isSingleMethod() makes the consideration my iterating through the array
of Method objects returned from Class.getMethods().
The API javadoc for Class.getMethods() [1] says (amongst other things):
"The elements in the array returned are not sorted and are not in any
particular order."
Indeed and this order even changed during JDK7 development.
However, isSingleMethod() currently relies upon any methods defined on
java.lang.Object appearing in the list before any others.
I suppose this happens to be the case currently (at least, when using
hotspot), but it is a generally brittle assumption for this code to rely
upon.
I don't know if the author actually made that assumption or whether the
code just happens to only work in that case, but it is certainly broken
logic.
Please find below a suggested change which removes this assumption by
making the algorithm agnostic to the ordering returned by
Class.getMethods().
I agree that the suggested change fixes the problem.
However, unless I'm missing something subtle, why do we need to check
for the method being abstract? Aren't all interface methods always
implicitly abstract?
Please consider this change for committal.
I'll let one of the libs team file a bug :)
Cheers,
David Holmes
Thanks,
Neil
[1]
http://download.oracle.com/javase/7/docs/api/java/lang/Class.html#getMethods%28%29