Nhibernate forces you to use an Iesi Set, instead of the net 4 ISet interface. In the following snippet of code I check whether an iesi set contains an item:
public virtual void Remove(Substance substance)
{
var test = _substances.First() == substance;
if (!_substances.Contains(substance)) return;
_substances.Remove(substance);
substance.SubstanceGroup = null;
}
The variable _substances references a HashedSet. I have added the test var just to check the code as a temporary measure. I have the Equals method overridden like this:
public override int GetHashCode()
{
return Equals(Id, default(TId)) ? base.GetHashCode() : Id.GetHashCode();
}
This causes the item to return the Id (Guid) as hash. If I check in the debugger I get the following result:
test
true
_substances.Contains(substance)
false
_substances.First().GetHashCode()
-2974953
substance.GetHashCode()
-2974953
How can it be that exactly the same object is not discovered in the collection using the contains method of that collection?? I can even do this in the debugger:
_substances.Contains(_substances.First())
false
Obviously, _substances.Remove(substance) doesn't work either. After some additional research I found out that NH replaces the collection with it's own Persistent Generic set. The problem arises when this set is used. If I retrieve an item from that set and I call Contains on the same set, it always returns false. I have overridden the GetHashCode and Equals, even put return true in the Equals method.