В чем разница между Object.Equals (obj, null) и obj == null - PullRequest
2 голосов
/ 09 августа 2011

Почти каждый раз, когда я хочу проверить равенство объекта на null Я использую обычную операцию проверки на равенство

if (obj == null)

Недавно я заметил, что я использую Object.Equals() чаще

if (Object.Equals(obj, null))

и, читая о проверке на ноль, я нашел это Является ли ReferenceEquals (null, obj) тем же, что и null == obj?

if (ReferenceEquals(null, obj))

Какая разница? и где / когда использовать каждый? плюс я обнаружил, что последние две проверки выглядят одинаково в соответствии с их summary

1 Ответ

13 голосов
/ 09 августа 2011

Object.Equals(x, y) будет:

  • Вернуть true, если x и y равны нулю
  • Вернуть false, если точно один из x или y равен нулю
  • В противном случае вызовите либо x.Equals(y), либо y.Equals(x) - это не должно иметь значение, какое. Это означает, что любое полиморфное поведение, реализованное типом времени исполнения объекта, на который ссылается x или y, будет вызвано.

ReferenceEquals будет не вызывать полиморфный метод Equals. Это просто сравнивает ссылки на равенство. Например:

string x = new StringBuilder("hello").ToString();
string y = new StringBuilder("hello").ToString();
Console.WriteLine(Object.Equals(x, y)); // True
Console.WriteLine(Object.ReferenceEquals(x, y)); // False
Console.WriteLine(x == y); // True due to overloading

Теперь, если вы только проверяете на ничтожность, тогда вы на самом деле не хотите полиморфное поведение - просто ссылаетесь на равенство. Так что не стесняйтесь использовать ReferenceEquals.

Вы можете также использовать ==, но это может быть перегружено (не переопределено) классами - это в случае строки, как показано выше. Наиболее распространенный случай использования ReferenceEquals в моем опыте - это когда вы внедряете ==:

public bool operator ==(Foo x1, Foo x2)
{
    if (ReferenceEquals(x1, x2))
    {
        return true;
    }
    if (ReferenceEquals(x1, null) || ReferenceEquals(x2, null))
    {
        return false;
    }
    return x1.Equals(x2);
}

Здесь вы действительно не хотите вызвать реализацию ==, потому что она будет повторяться вечно - вам нужна очень определенная семантика равенства ссылок.

...