views:

122

answers:

4
+2  Q: 

GetHashCode issue

Hi,

Can anyone help explain the following. I am having an issue with a Dictionary where ContainsKey evaluates to false while both Equals and GetHashCode for the objects are successful. Below is the output from the immediate window in Visual Studio:

?LocationToRackingGroup.Keys.ToArray()[23].Equals(location)
true
?LocationToRackingGroup.Keys.ToArray()[23] == (location)
true
?this.LocationToRackingGroup.ContainsKey(location)
false

Am I missing something? Any ideas are much appreciated.

Cheers,

James

+4  A: 

Is location mutable? Because if it is, it might have changed since you put it into the dictionary.

Robert Giesecke
Oh, very true - good spot; a common cause of pain.
Marc Gravell
+3  A: 

Well, I'd want to look at a couple of things:

1: is GetHashCode correctly implemented:

?LocationToRackingGroup.Keys.ToArray()[23].GetHashCode() == location.GetHashCode()

2: if this is the generic dictionary, does the type also implement (explicitly) IEquatable<Location>

3: did you supply a custom IEqualityComparer<Location> to the dictionary in the constructor?

To rule out the last, perhaps look at:

?LocationToRackingGroup.Comparer.Equals(blah23, location); // should be true
?LocationToRackingGroup.Comparer.GetHashCode(blah23);  // should equal below
?LocationToRackingGroup.Comparer.GetHashCode(location);// should equal above
Marc Gravell
Thanks for the quick response:1. GetHashCode is equal for both, I meant to include that sorry:?LocationToRackingGroup.Keys.ToArray()[23].GetHashCode()973699796location.GetHashCode()9736997962. I hadn't implemented IEquatable explicitly but have just tried that and it made no difference I am afraid.3. I don't think this should make a difference. If I am correct it should use the default IEqualityComparer Equals which has been overriden.Any other ideas?
James
Have you looked at Robert's answer? Other than that, we'd probably need something reproducible.
Marc Gravell
A: 

The rule is that the hashcode must be the same for every 'instance' of the same data. If it changes, then your hash function is broken.

IOW, the safest hash function is:

int GetHashcode()
{
  return 0;
}
leppie
This defeats the usefulness of the hash code method, but is technically a legal implementation; might be helpful to try this for debugging
RMorrisey
+1  A: 

OK, this is a long shot.

In the first two lines you refer to LocationToRackingGroup and in the last to this.LocationToRackingGroup, are they the same variable?

Peter van der Heijden