[concurrency-interest] Reference/IdentityMap toString

Jed Wesley-Smith jwesleysmith at atlassian.com
Fri Aug 20 02:39:38 EDT 2010


I think you're basically arguing that IdentityHashMap (and any "map" or 
"set" that uses identity == rather than the equals contract) is broken. 
Which, is of course true – and there is a lot of prior discussion 
recognising that it was probably a mistake but a pragmatically useful 
one nonetheless in expert hands.

Personally I find the fact that equals is defined at all on Object (or 
at least to be a virtual method) a problem. It is extremely hard to 
maintain the symmetric and transitive properties of the contract if your 
classes are open. It is maintainable when you tightly control your class 
hierarchy and object instantiation but can be the source of lots of 
problems in a n open environment.

So, should CCHM and IHM provide a special toString() to indicate they 
are broken? Personally it seems a quite esoteric requirement. Better not 
to use them in the first place unless you really, really need to and 
even then hide it from the hoi polloi.

If you really need to have the example below work both conceptually and 
print a nice toString have a Ref class that contains a single final 
reference and delegates its equality to the contained reference identity. eg

class Ref<T> {
final T ref;

Ref(T ref) {
this.ref = ref;

T get() {return ref;}

public String toString() {return ref.getClass().getName() + "@" + 

public int hashCode() {return System.identityHashCode(ref);}

public boolean equals(Object o) {return ref == ((Ref) o).ref);}

This gives you total control and means you don't need to use the IHM or 
CCHM. In the IHM case this means the extra indirection of a wrapper, but 
CCHM I believe does this anyway. (Of course, CCHM can also do weak/soft 
refs and a few other things…)


Jason Mehrens wrote:
> Kasper,
> > You still haven't come up with any convincing use case.
> Feel free to counter each of my previous points.
> >I've never seen any bugs related to this behavior.
> Take the output of this code:
> //===============
> Map<Integer, Integer> id = new IdentityHashMap<Integer, Integer>();
> id.put(new Integer(1), new Integer(1));
> id.put(new Integer(1), new Integer(1));
> id.put(new Integer(1), new Integer(1));
> System.out.println(id.keySet());
> //==============
> Shouldn't a set contain unique items? If you are tracking items by 
> identity or reference displaying the contents of a key/value has no 
> meaning. I don't think I would get any positive feedback if I wrote 
> the output of that code on a piece of paper and presented it as an 
> example of a unique set of elements.
> >And if you want a custom toString
> > method for CCHM you can just use the CCHM.entrySet().iterator to 
> iterate
> > through all elements and print whatever you want.
> That applies both ways.
> >Requiring people to
> > implement a toString(Object) method whenever they implement the
> > Equivalence interface is just a waste of peoples time IMO.
> Equivalence is extracting methods from Object. The object 
> documentation states they subclasses should always override toString. 
> Currently, there is no way translate that requirement from Object to 
> Equivalence.
> Regards,
> Jason
> ------------------------------------------------------------------------
> _______________________________________________
> Concurrency-interest mailing list
> Concurrency-interest at cs.oswego.edu
> http://cs.oswego.edu/mailman/listinfo/concurrency-interest

More information about the Concurrency-interest mailing list