C#“为”投与经典剧组
可能重复:
投射vs在CLR中使用'as'关键字
我最近了解到一种不同的投射方式。 而不是使用
SomeClass someObject = (SomeClass) obj;
你可以使用这个语法:
SomeClass someObject = obj as SomeClass;
如果obj不是SomeClass,它似乎返回null,而不是抛出类转换异常。
我发现如果转换失败,可能会导致NullReferenceException,并尝试访问someObject变量。 所以我想知道这种方法的基本原理是什么? 为什么要使用这种铸造方式而不是(旧的) - 它似乎只是将“失败”的问题转移到代码中。
使用“经典”方法,如果转换失败,则抛出异常。 使用as方法,它会导致null,它可以被检查,并避免抛出异常。
另外,只能对引用类型使用“as”,所以如果要将类型转换为值类型,则仍然必须使用“经典”方法。
注意:
as
方法只能用于可以赋予null
值的类型。 这只能用于表示引用类型,但是当.NET 2.0推出时,它引入了可为空的值类型的概念。 由于这些类型可以分配一个null
值,因此它们可以与as
运算符一起使用。
空比较是远远超过抛出和捕获异常快。 异常有很大的开销 - 堆栈跟踪必须被组装等。
异常应该代表一个意想不到的状态,这往往并不代表情况(这是在as
更好地工作)。
在某些情况下,很容易处理null
不是异常。 特别是,合并运算符很方便:
SomeClass someObject = (obj as SomeClass) ?? new SomeClass();
它还简化了你所在的代码(不使用多态性),并基于对象的类型进行分支:
ClassA a;
ClassB b;
if ((a = obj as ClassA) != null)
{
// use a
}
else if ((b = obj as ClassB) != null)
{
// use b
}
按照MSDN页面的规定, as
运算符等同于:
expression is type ? (type)expression : (type)null
它避免了完全支持更快类型测试的异常,而且将其用于支持null
类型(引用类型和Nullable<T>
)。