I am quite certain that we have not covered all the bases for equals operations (and perhaps comparisons too), and it would be good to have a more complete test base for == and =:=.
We need to evaluate what java.lang.Object.equals() should be bound to, ==, =:= or something else. I think it needs to be bound to =:= (so that e.g. 0 and 0.0 are different in equals/hash maps).
Perhaps, to make things perfectly clear, EObject should have erl_equals(other) and erl_equals_exact(other); and then have EObject.equals(java.lang.Object) call one of those.
But before we can commence, we need some more consistent test.
I can make a comparison test case for this.
Don't know if that's what you had in mind - I guess we need to cover all kinds of list representations, for example? - but it will be a start (and is easy to make).
I see you did that...
I've made some amendments: Firstly, there's no reason to compare both ways - the matrix test style takes care of that. Secondly, we need to cover e.g. all possible list representations. Ideally, we should check that equal_tests has complete code coverage of the comparison code...
I found an issue; it appears to be in EBigString.
Fixed - but found another case: "ab" vs [97.0, 98.0].
Not sure if compare_same() is supposed to implement '==' or '=:=' ?
Compare same is supposed to be used for < > =< etc. Is (A >= B) and (A =< B) equivalent to == or =:= ? I would presume ==. Hence, compare_same() should implement ==-ish semantics.
Regarding the bug that "ab" =:= [97.0, 98.0] yields true right now, equalsExactly() for all lists needs to apply equalsExactly to it's pointwise elements.
OK. Then the problem is that EObject.equalsExactly() calls compareTo() which uses compare_same(). And the only list classes which overrides equalsExactly() are EString and EBigString; EList inherits the EObject version.
I don't know if the EObject version makes much sense; could be it should be declared abstract instead. It certainly doesn't work for composite terms (and the atomic once all seem to override it).
(An observation: if we want compareTo() to behave like Erlang's '<', and equals() to behave like Erlang's '=:=', then compareTo() is not "consistent with equals"; this is allowed, but sorted collections then won't work for these objects.)
At present we have the problem that
The solution which I can see is to make equals() have exact-match semantics, and adapt the TreeSet used in ETS so that on insertion, all key objects are wrapped in an adapter which redirects equals() to compareSame(). (Yes, as described that'll be two adapters - one for TreeSets and one for their keys. The latter one is the essential one though.)