У меня есть класс сущностей, как это (с большим количеством вещи пропали без вести):Как Contains возвращает false, но GetHashCode() возвращает одинаковое число, а Equals возвращает true?
class Parent
{
private readonly Iesi.Collections.Generic.ISet<Child> children =
new Iesi.Collections.Generic.HashedSet<Child>();
public virtual void AddChild(Child child)
{
if (!this.children.Contains(child))
{
this.children.Add(child);
child.Parent = this;
}
}
public virtual void RemoveChild(Child child)
{
if (this.children.Contains(child))
{
child.Parent = null;
this.children.Remove(child);
}
}
}
Однако при попытке удалить ребенка, то if
заявление оценивает в false
. Итак, я ставлю точку останова на if
заявлении, и оценивали определенные выражения:
this.children.Contains(child) => false
this.children.ToList()[0].Equals(child) => true
this.children.ToList()[0].GetHashCode() => 1095838920
child.GetHashCode() => 1095838920
Я понимаю, что если GetHashCode
возвращает одинаковые значения, то затем проверяет Equals
. Почему Contains
возвращает false?
Оба моих Parent
и Child
сущностей наследует от общего Entity
базового класса, которая не является унифицированной версией родового объекта базового класса со страницы 25 NHibernate 3.0 Cookbook. Вот мой базовый класс:
public class Entity : IEntity
{
public virtual Guid Id { get; private set; }
public override bool Equals(object obj)
{
return Equals(obj as Entity);
}
private static bool isTransient(Entity obj)
{
return obj != null &&
Equals(obj.Id, Guid.Empty);
}
private Type getUnproxiedType()
{
return GetType();
}
public virtual bool Equals(Entity other)
{
if (other == null)
return false;
if (ReferenceEquals(this, other))
return true;
if (!isTransient(this) &&
!isTransient(other) &&
Equals(Id, other.Id))
{
var otherType = other.getUnproxiedType();
var thisType = getUnproxiedType();
return thisType.IsAssignableFrom(otherType) ||
otherType.IsAssignableFrom(thisType);
}
return false;
}
public override int GetHashCode()
{
if (Equals(Id, Guid.Empty))
return base.GetHashCode();
return Id.GetHashCode();
}
}
После дальнейшего изучения, я чувствую, что-то подобное происходит:
- Вызов
parent.AddChild(child)
- Сохранение в базе данных, что привело
child.Id
к генерироваться - Телефон:
parent.RemoveChild(child)
... и как обсуждалось ниже, это менялось GetHashCode()
.
Это было результатом ошибки в моей программе - я должен был перезагрузить parent
между шагами 2 и 3.
Тем не менее, я думаю, что есть что-то более принципиально неправильно.
Из любопытства, не могли бы вы проверить его с 'частных Iesi.Collections.Generic.HashedSet детей = новый Iesi.Collections.Generic.HashedSet ();' –