Подтвердить что ты не робот

Какая точка ключевого слова "Как" в С#

Из документов:

Оператор as подобен кастингу, за исключением того, что он дает нулевое значение для отказа преобразования, а не для создания исключения. Более формально выражение вида:

   expression as type

эквивалентно:

  expression is type ? (type)expression : (type) null

за исключением того, что выражение оценивается только один раз.

Так почему бы вам не выбрать, чтобы сделать это так или иначе. Почему две системы литья?

4b9b3361

Ответ 1

Это не две системы кастинга. У обоих есть подобные действия, но очень разные значения. "Как" означает "Я думаю, что этот объект может быть действительно другого типа, дайте мне null, если это не так". Бросок означает одну из двух вещей:

  • Я точно знаю, что этот объект на самом деле относится к этому другому типу. Сделайте это так, и если я ошибаюсь, сбой программы.

  • Я точно знаю, что этот объект не относится к этому другому типу, но существует известный способ преобразования значения текущего типа в желаемый тип. (Например, приведение int в short.) Сделайте так, и если преобразование действительно не работает, выполните сбой программы.

Более подробную информацию см. в моей статье на эту тему.

http://blogs.msdn.com/b/ericlippert/archive/2009/10/08/what-s-the-difference-between-as-and-cast-operators.aspx

Ответ 2

Потому что иногда вы хотите, чтобы что-то не сработало, если вы не можете делать такие роли, как вы ожидаете, и в другие моменты вам все равно, и просто хотите отбросить данный объект, если он не может выполнить бросок.

В основном это более быстрая версия обычного литья, завернутая в блок try; но As является более читаемым и также сохраняет ввод текста.

Ответ 3

Эффективность и производительность

Часть выполнения броска - это некоторая интегрированная проверка типов; поэтому префикс фактического акта с явной проверкой типов избыточен (проверка типа происходит дважды). Использование ключевого слова as гарантирует выполнение только одного типа проверки. Вы можете подумать "но он должен выполнить нулевую проверку вместо второй проверки типа", но проверка нулевого значения очень эффективна и эффективна по сравнению с проверкой типов.

if (x is SomeType )
{
  SomeType y = (SomeType )x;
  // Do something
}

выполняет 2x проверки, тогда как

SomeType y = x as SomeType;
if (y != null)
{
  // Do something
}

делает 1x - нулевая проверка очень дешева по сравнению с проверкой типа.

Ответ 4

Он позволяет выполнять быструю проверку без накладных расходов при попытке/литье, которые могут потребоваться в некоторых случаях для обработки деревьев наследования, основанных на сообщениях.

Я использую его довольно много (получаю сообщение, реагирую на определенные подтипы). Попытка/бросок будет значительно медленнее (многие попытки/улавливают кадры на каждом проходящем сообщении), и мы говорим об обработке 200 000 сообщений в секунду здесь.

Ответ 5

Обычно я выбираю тот или иной, основанный на семантике кода.

Например, если у вас есть object, что вы знаете, что он должен быть string, то используйте (string), потому что это говорит о том, что человек, записывающий код, уверен, что объект является string, и если это не то, что у нас уже есть большие проблемы, чем исключение, выполняемое во время выполнения, которое будет выбрано.

Используйте as, если вы не уверены, что объект имеет определенный тип, но для него требуется логика. Вы можете использовать оператор is, за которым следует бросок, но оператор as более эффективен.

Ответ 6

Позвольте мне дать вам реальные сценарии того, где вы будете использовать оба.

public class Foo
{
  private int m_Member;

  public override bool Equals(object obj)
  {
    // We use 'as' because we are not certain of the type.
    var that = obj as Foo;
    if (that != null)
    {
      return this.m_Member == that.m_Member;
    }
    return false;   
  }
}

А...

public class Program
{
  public static void Main()
  {
    var form = new Form();
    form.Load += Form_Load;
    Application.Run(form);
  }

  private static void Form_Load(object sender, EventArgs args)
  {
    // We use an explicit cast here because we are certain of the type
    // and we want an exception to be thrown if someone attempts to use
    // this method in context where sender is not a Form.
    var form = (Form)sender;

  }
}

Ответ 7

Возможно, примеры помогут:

// Regular casting
Class1 x = new Class1();
Class2 y = (Class2)x; // Throws exception if x doesn't implement or derive from Class2

// Casting with as
Class2 y = x as Class2; // Sets y to null if it can't be casted.  Does not work with int to short, for example.

if (y != null)
{
  // We can use y
}

// Casting but checking before.
// Only works when boxing/unboxing or casting to base classes/interfaces
if (x is Class2)
{
  y = (Class2)x; // Won't fail since we already checked it
  // Use y
}

// Casting with try/catch
// Works with int to short, for example.  Same as "as"
try
{
  y = (Class2)x;
  // Use y
}
catch (InvalidCastException ex)
{
  // Failed cast
}