C#Equals扩展无法检查相等性

C#Equals扩展无法检查相等性,c#,reflection,equality,C#,Reflection,Equality,我扩展了equals方法和hashcode来检查两个具有布尔属性的相同对象的相等性。当我改变对象使其中一个布尔属性为false而不是true时,它无法识别差异并断言它们相等;。你知道为什么吗 public override bool Equals(object value) { if (!(value is LocationPropertyOptions options)) return false; return Equa

我扩展了equals方法和hashcode来检查两个具有布尔属性的相同对象的相等性。当我改变对象使其中一个布尔属性为false而不是true时,它无法识别差异并断言它们相等;。你知道为什么吗

   public override bool Equals(object value)
    {
        if (!(value is LocationPropertyOptions options))
            return false;

        return Equals(options, value);
    }

    public bool Equals(LocationPropertyOptions options)
    {
        return options.GetHashCode() == GetHashCode();
    }

    public override int GetHashCode()
    {
        return ToString().GetHashCode();
    }

    public override string ToString()
    {
        return $"{Identifier}{AccountEntityKey}{Address}{Comments}{Contact}" +
               $"{Coordinate}{Description}{FaxNumber}{LastOrderDate}{PhoneNumber}" +
               $"{ServiceAreaOverride}{ServiceRadiusOverride}{StandardInstructions}" +
               $"{WorldTimeZone_TimeZone}{ZoneField}{CommentsOptions}";
    }

您可以从
value
中选择
options
,然后使用
options
vs
value
调用
Equals
。这意味着您将
进行比较,它将始终为您返回
真值

public override bool Equals(object value)
{
    if (!(value is LocationPropertyOptions options))
       return false;    
    return Equals(options, value);
}
尝试将
进行比较,如

return Equals(this, value);

您可以从
value
中选择
options
,然后使用
options
vs
value
调用
Equals
。这意味着您将
进行比较,它将始终为您返回
真值

public override bool Equals(object value)
{
    if (!(value is LocationPropertyOptions options))
       return false;    
    return Equals(options, value);
}
尝试将
进行比较,如

return Equals(this, value);

这并不能真正回答你的问题。但是,在实现相等时,应该考虑一些事情来避免这种错误。 首先,您有两个完全不同的实现来表示相等。您的
override bool Equals(object value)
重定向到静态方法
object.Equals(object,object)
,该方法只执行
ReferenceEquals
。另一方面,您的
public bool Equals(LocationPropertyOptions)
(可能是
IEquatable
的一个实现)只需使用奇怪的
GetHashCode
-实现即可

第二点:您不应该在hashcode实现中使用可变成员,特别是当您的对象存储在字典或hashmap中时,这在很大程度上取决于hashcode的良好实现。看

可以为不可变引用类型重写GetHashCode()。在里面 常规,对于可变引用类型,应该重写 GetHashCode()仅适用于以下情况:

  • 您可以从不可变的字段计算哈希代码;或

  • 您可以确保可变对象的哈希代码不会更改 而对象包含在依赖其哈希的集合中 代码

第三点也是最后一点:在检查是否相等时,不应使用
GetHashCode

不要测试散列码是否相等,以确定两个 对象是平等的

虽然假定相等的对象具有相同的哈希代码,但不同的对象可能具有完全相同的哈希代码。因此,相等的哈希代码只是两个实例可能相等的指示器

两个相等的对象返回相等的哈希代码。然而, 反之亦然:相等的哈希代码并不意味着对象 相等,因为不同(不相等)对象可以具有相同的哈希 代码[…]
您不应该假设相等的哈希代码意味着对象相等


这并不能真正回答你的问题。但是,在实现相等时,应该考虑一些事情来避免这种错误。 首先,您有两个完全不同的实现来表示相等。您的
override bool Equals(object value)
重定向到静态方法
object.Equals(object,object)
,该方法只执行
ReferenceEquals
。另一方面,您的
public bool Equals(LocationPropertyOptions)
(可能是
IEquatable
的一个实现)只需使用奇怪的
GetHashCode
-实现即可

第二点:您不应该在hashcode实现中使用可变成员,特别是当您的对象存储在字典或hashmap中时,这在很大程度上取决于hashcode的良好实现。看

可以为不可变引用类型重写GetHashCode()。在里面 常规,对于可变引用类型,应该重写 GetHashCode()仅适用于以下情况:

  • 您可以从不可变的字段计算哈希代码;或

  • 您可以确保可变对象的哈希代码不会更改 而对象包含在依赖其哈希的集合中 代码

第三点也是最后一点:在检查是否相等时,不应使用
GetHashCode

不要测试散列码是否相等,以确定两个 对象是平等的

虽然假定相等的对象具有相同的哈希代码,但不同的对象可能具有完全相同的哈希代码。因此,相等的哈希代码只是两个实例可能相等的指示器

两个相等的对象返回相等的哈希代码。然而, 反之亦然:相等的哈希代码并不意味着对象 相等,因为不同(不相等)对象可以具有相同的哈希 代码[…]
您不应该假设相等的哈希代码意味着对象相等


这绝对不是平等的安全实现。两个字符串可以不同并且具有相同的哈希代码。您还假设所有这些值都有合理的字符串实现,并且它们完全与相等相关,这很可能不是真的,而且无论哪种方式,比较连接的字符串都不是确保所有基础值都相同的安全方法。您需要比较实际值。不要在hashcode实现中使用可变成员,至少不要像实例存储在字典或hashmap中那样复杂。除此之外,您不应该依赖hashcode来实现均一性。相等的哈希代码并不一定意味着两个对象相等,它只是一个指示符。顺便说一句,你应该仔细看一下:为什么你要将调用
bool Equals(object value)
的命令重定向到
object.Equals(object,object)
,而
bool Equals(LocationPropertyOptions)
只使用
GetHashCode
。通常,所有的等式比较都应该做e