zoukankan      html  css  js  c++  java
  • c# 优化代码的一些规则——使用is或as和强制类型转换的区别[三]

    前言

    使用as和强制类型转换的时候的区别是否仅仅是代码形式上的区别。

    答案是肯定不是的。

    正文

    看两段代码:

    object o = Factory.GetObject();
    Student student = o as Student;
    if (student != null)
    {
    	//dosomething
    }
    

    object o = Factory.GetObject();
    Student student = o as Student;
    try
    {
    	Student student = (Student)o;
    	if (student != null)
    	{
    		//dosomething
    	}
    }
    catch (InvalidCastException e)
    {
    	var str = e.Message;
    }
    

    问题来了,这两者有什么区别?

    首先第二个里面有一个损失性能的地方,就是try{}catch{}。

    那么可以肯定一点就是在程序健壮性相同的情况下,使用as最好。

    问题又出现了,那么什么时候不能用as呢?或者as 和 强制类型转换之间差别是什么呢?

    as 转换的局限性在于,他只会做简单的装箱和拆箱工作,而不会去做一些类型转换。

    也就是说,如果待转换的对象既不属于目标对象,也不属于派生出来的类型那么是不能转换的。

    这里就有人奇怪了,如果两者都不属于那么转换失败正常啊。

    怎么说呢,请考虑下面两种情况:

    1.数值之间转换,比如int转long之类的。

    2.自己实现转换,如:implicit

    这两者as搞不定的。

    比如说:

    有一个child 类,想转学生类。

    这样写:

    public class Child
    {
    	public static implicit operator Student(Child child)
    	{
    		return new Student();
    	}
    }
    

    然后我来这样写:

    object o = Factory.GetObject();
    Student student = o as Student;
    if (student != null)
    {
    	//dosomething
    }
    

    GetObject为:

    public static implicit operator Student(Child child)
    {
    	return new Student();
    }
    

    这样写是不成功的。

    图我贴出来了。

    那么我这样写,是否能成功呢?

    object o = Factory.GetObject();
    try
    {
    	Student student = (Student)o;
    	if (student != null)
    	{
    		//dosomething
    	}
    }
    catch (InvalidCastException e)
    {
    	var str = e.Message;
    }
    

    遗憾的是,这样写也是失败的。

    那么为什么失败呢?

    C# 有一个编译期和一个运行期。

    而强制转换发送在编译期。

    也就是说它读取的是object能不能转换为Student,而不是在运行期的Child。

    好的,那么你可以这样。

    object o = Factory.GetObject();
    var c = o as Child;
    try
    {
    	Student student = (Student)c;
    	if (student != null)
    	{
    		//dosomething
    	}
    }
    catch (InvalidCastException e)
    {
    	var str = e.Message;
    }
    

    这样是对的,但是对于编程学来说,谁会去这样写呢,在很多时候我们应该尽量避免装箱和拆箱。

    在此总结一下,那就是as 运行在运行期,而cast 在编译期。

    好的,as 完了后,看下is吧。

    is 是遵守多态的,多态很好理解哈。

    所以is 不是==的意思,而是是否是自己或者子类的意思。

    如果你想要去得到具体的类型判断,那么请使用getType更为合适。

    总结

    使用as或者 强制类型转换没有定性的要求,看具体的方案,然后呢当可以使用as的时候尽量使用as,毕竟可以避免try catch这种消耗性能的东西。

  • 相关阅读:
    解决Laravel错误1071 Specified key was too long的多种方法
    优雅笔记
    Centos 发布docker(二)
    centOS7虚拟机设置固定IP
    开启Docker远程访问
    docker.service: Failed with result ‘exit-code‘
    jpa 中 page.map 方法的使用
    Xshell 通过ssh 连接主机
    JeecgBoot Minio版本6.0.13升级到8.0.3修改方法
    gateway 跨域
  • 原文地址:https://www.cnblogs.com/aoximin/p/12965408.html
Copyright © 2011-2022 走看看