((Система. Объект) p == пустой указатель)

Почему делают это:

    // If parameter cannot be cast to Point return false.
    TwoDPoint p = obj as TwoDPoint;
    if ((System.Object)p == null)
    {
        return false;
    }

Вместо этого:

    // If parameter cannot be cast to Point return false.
    TwoDPoint p = obj as TwoDPoint;
    if (p == null)
    {
        return false;
    }

Я не понимаю, почему Вы когда-либо писали бы ((Система. Объект) p)?

С уважением,

Dan

5
задан Daniel James Bryars 25 May 2010 в 21:34
поделиться

5 ответов

Вы приводите к object, когда не знаете или не можете быть уверены, что исходный класс переопределил operator ==:

using System;
class AlwaysEqual
{
    public static bool operator ==(AlwaysEqual a, AlwaysEqual b)
    {
        return true;
    }

    public static bool operator !=(AlwaysEqual a, AlwaysEqual b)
    {
        return true;
    }
}


class Program
{
    static void Main()
    {
        object o = new AlwaysEqual();
        AlwaysEqual ae = o as AlwaysEqual;

        if (ae == null)
        {
            Console.WriteLine("ae is null");
        }

        if ((object)ae == null)
        {
            Console.WriteLine("(object)ae is null");
        }
    }
}

Этот код выводит only "ae is null", что явно не соответствует действительности. Приведение к object позволяет избежать AlwaysEqual класса operator == и поэтому является истинной проверкой ссылки на null.

12
ответ дан 18 December 2019 в 10:42
поделиться

Каждый объект в .NET является производным от System.Object, поэтому нет необходимости в явном приведении.

1
ответ дан 18 December 2019 в 10:42
поделиться

Говоря простым языком, это бессмысленно. Null всегда может быть присвоен (за исключением non-nullables, таких как ints и structs) независимо от типа, поэтому его всегда можно проверить. Приведение не обязательно

Если TwoDPoint является не нулевым типом, таким как struct, то у него действительно может быть точка. Кэш (System.Object) фактически превратит struct в объект с нулевым значением. Но если бы это было так, то obj as TwoDPoint был бы недействителен. Вам понадобится obj as TwoDPoint?, чтобы сделать его nullable. (нельзя использовать as с ненулевыми объектами)

1
ответ дан 18 December 2019 в 10:42
поделиться

И еще более кратким будет:

if (!(obj is TwoDPoint)) {
  return false;
}
1
ответ дан 18 December 2019 в 10:42
поделиться

Это имеет смысл, если этот код находится внутри переопределения Object.Equals и вы не хотите вызывать оператор равенства (который может, например, ошибочно вызвать Equals ) . Приведение к объекту позволяет вызвать стандартный оператор равенства, который сравнивает ссылки.

Обычно используется Object.ReferenceEquals для сравнения экземпляра объекта с null внутри переопределения Equals .

Например, это может вызвать переполнение стека:

public class Point {
  public override bool Equals (object other) {
    var otherPoint = other as Point;

    if (other == null)
      return false;

    //...
  }

  public static bool operator == (Point l, Point r) {
    //...
    //null checks
    if (!l.Equals(r))
      return false;
  }
}

В приведенном выше примере оператор равенства вызывает Equals и потому, что переменная otherPoint имеет тип Point , он вызовет оператор равенства, вызывая бесконечную рекурсию.

Обычно, когда вы переопределяете Equals и определяете оператор равенства, вы помещаете логику сравнения в оператор и вызываете ее из переопределения Equals . Имейте в виду, что рекомендуется, чтобы класс был неизменным, если оба они переопределены.

public class Point {
  public override bool Equals (object other) {
    var otherPoint = other as Point;
    return this == otherPoint;
  }

  //must override GetHashCode() as well

  public static bool operator == (Point l, Point r) {
    if (Object.ReferenceEquals(l, null) && Object.ReferenceEquals(r, null))
      return true;
    if (Object.ReferenceEquals(l, null) || Object.ReferenceEquals(r, null))
      return false;
    //actual equality checks
  }
  public static bool operator != (Point l, Point r) {
    return !(l==r);
  }
}
1
ответ дан 18 December 2019 в 10:42
поделиться
Другие вопросы по тегам:

Похожие вопросы: