Я задавался вопросом об этом, поэтому я думаю, что спрошу.
В большинстве мест, где вы увидите, используется та же семантическая логика для переопределения Equals, что и в GetHashCode для поэлементного равенства ... однако они обычно используют разные реализации:
public override bool Equals(object obj)
{
if (obj == null || GetType() != obj.GetType())
{
return false;
}
var other = (MyType)obj;
if (other.Prop1 != Prop1)
{
return false;
}
return true;
}
public override int GetHashCode()
{
int hash = -657803396;
num ^= Prop1.GetHashCode();
return num;
}
Если вы реализуете пословное равенство для своего типа (скажем, для сохранения в словарь), почему бы просто не переопределить GetHashCode, а затем сделать что-то вроде этого для Equals:
public override bool Equals(object obj)
{
return this.HashEqualsAndIsSameType(obj);
}
public static bool HashEquals(this object source, object obj)
{
if (source != null && obj != null)
{
return source.GetHashCode() == obj.GetHashCode();
}
if (source != null || obj != null)
{
return false;
}
return true;
}
public static bool HashEqualsAndIsSameType<T>(this T source, object obj)
{
return (obj == null || obj.GetType() == typeof(T)) && source.HashEquals(obj);
}