如何在没有无限递归的'=='运算符重载中检查空值?

And*_*nes 110 .net c# operator-overloading

以下将导致==运算符重载方法的无限递归

    Foo foo1 = null;
    Foo foo2 = new Foo();
    Assert.IsFalse(foo1 == foo2);

    public static bool operator ==(Foo foo1, Foo foo2) {
        if (foo1 == null) return foo2 == null;
        return foo1.Equals(foo2);
    }
Run Code Online (Sandbox Code Playgroud)

我如何检查空值?

Abe*_*cht 132

用途ReferenceEquals:

Foo foo1 = null;
Foo foo2 = new Foo();
Assert.IsFalse(foo1 == foo2);

public static bool operator ==(Foo foo1, Foo foo2) {
    if (object.ReferenceEquals(null, foo1))
        return object.ReferenceEquals(null, foo2);
    return foo1.Equals(foo2);
}
Run Code Online (Sandbox Code Playgroud)

  • 注意:相同的解决方案,但语法更简单:`if (foo1 is null) return foo2 is null;` (4认同)

And*_*nes 19

在重载方法中转换为对象:

public static bool operator ==(Foo foo1, Foo foo2) {
    if ((object) foo1 == null) return (object) foo2 == null;
    return foo1.Equals(foo2);
}
Run Code Online (Sandbox Code Playgroud)

  • 对于未来的访问者 - 接受的答案是一个函数,它执行对象的==.这基本上与接受的答案相同,但有一个缺点:需要演员.因此,得到的答案是优越的. (2认同)

Jon*_*ams 8

使用ReferenceEquals.来自MSDN论坛:

public static bool operator ==(Foo foo1, Foo foo2) {
    if (ReferenceEquals(foo1, null)) return ReferenceEquals(foo2, null);
    if (ReferenceEquals(foo2, null)) return false;
    return foo1.field1 == foo2.field2;
}
Run Code Online (Sandbox Code Playgroud)


jac*_*kbe 7

如果您使用的是 C# 7 或更高版本,则可以使用空常量模式匹配:

public static bool operator==(Foo foo1, Foo foo2)
{
    if (foo1 is null)
        return foo2 is null;
    return foo1.Equals(foo2);
}
Run Code Online (Sandbox Code Playgroud)

这为您提供了比调用 object.ReferenceEquals(foo1, null) 的代码更简洁的代码

  • 或`public static bool operator==( Foo foo1, Foo foo2 ) => foo1?.Equals( foo2 ) ?? foo2 为空;` (5认同)