加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

在.Net / C#中,是空密类型的?

发布时间:2020-12-15 06:46:39 所属栏目:百科 来源:网络整理
导读:null有一个类型?如何在内部表示一个空值?以下代码发生了什么? void Foo(string bar) {...}void Foo(object bar) {...}Foo((string)null); 编辑:迄今为止的答案是非特定的和太高的级别.引用类型对象由一个指向堆栈的指针组成,它指向堆上的一个位置,它包含
null有一个类型?如何在内部表示一个空值?以下代码发生了什么?
void Foo(string bar) {...}
void Foo(object bar) {...}

Foo((string)null);

编辑:迄今为止的答案是非特定的和太高的级别.引用类型对象由一个指向堆栈的指针组成,它指向堆上的一个位置,它包含同步块索引,类型句柄和对象的字段.当我将一个对象的实例设置为null时,堆栈上的指针指向哪里?而在代码片段中,C#编译器简单地使用的转换来决定要调用哪个重载,并且没有真正的任何转换为??null?

我正在寻找一个了解CLR内部人员的深入回答.

解决方法

代码示例中的转换字符串不会给null一个类型,因为null不能有类型本身.如果你想证明这一点,那么执行下面的代码,你可以看到null总是等于它自己,不管它分配给哪个类型的变量是:
string s = null;
IPAddress i = null;
Console.WriteLine(object.Equals(s,i)); // prints "True"
Console.WriteLine(object.ReferenceEquals(s,i)); // prints "True"

演员所做的是告诉编译器选择哪个重载.由于null没有类型,因此不知道是否选择接受对象或字符串的重载,因为值可以被解释为.所以你正在帮助它说“这是一个空值,应该被视为一个字符串”.

如果你想看看下面发生了什么,那么看看你的代码中的IL.方法调用的相关位在文本IL中类似于以下内容(取决于您的命名空间和类名等):

ldnull 
call void ConsoleApplication1.Program::Foo(string)

所以发生这种情况的是,在堆栈中加载一个空值,然后由占用字符串的重载消耗,因为在编译时执行重载分辨率,所以调用方法被烧录到IL中.

如果你想看看ldnull的作用,以及为什么不像使用像ldc.i4.0这样的东西把零加载到堆栈上,那么看到this answer(如果你不想跟随链接,原因是它是否则不存在于CLR中的大小不相关的零).

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读