如何在.NET中实现值类型

时间:2010-03-27 10:13:46

标签: .net

一直在寻找网络,找不到任何关于如何实际实施价值类型的文章。

例如,Int32是一个结构体,它的直接父元素是System.ValueType,它的最终父元素是System.Object。对象是一个类 - 我想ValueType是一个类?

班级等级是什么? CLR必须扮演什么角色?在什么阶段以及CLR如何知道将值类型分配给堆栈? (仅供参考,我知道值类型存储在声明的位置)。

3 个答案:

答案 0 :(得分:1)

值类型由各种语言编译器和CLR专门处理。很简单,CLR知道从ValueType派生的所有内容都是按值传递的,并且本地ValueType变量存在于堆栈中。

我不知道在没有徘徊于“实现定义”领域的情况下,有多少可以说出价值类型。

答案 1 :(得分:1)

在这种情况下,类层次结构有点人为。类型是引用还是值类型直接存储在类型元数据中,因此CLR不需要查看它是否派生自System.ValueType。但System.ValueType确实有所帮助 - 它实现了值均衡检查和GetHashCode()。

CLR为堆栈中的任何局部变量分配空间,该变量在其元数据中标记为“.class value”。何时发生这种情况取决于代码是否优化。如果没有进行优化,那么它会在声明中发生以帮助调试。如果它被优化,那么可能会尽可能晚,但这取决于实现。

我不知道还有什么可说的,因为你的问题相当广泛,因为它目前的措辞。

答案 2 :(得分:1)

烟雾和镜子是描述它的最佳方式。我会好好的。值类型不支持继承,也不能具有虚方法。但是,int类型具有ToString()和GetHashCode()方法,这两种方法都是虚方法。它从System.Object继承它们。

这种魔法来自拳击转换。有专门的IL操作码执行它,OpCodes.Box和OpCodes.Constrained。这会将值类型转换为对象,该对象存储原始值类型的值。反过来也是如此,取消装箱会将对象转换回值类型。

如果你有一个好的.NET编译器,比如C#,那你就不会自己明确调用转换。当需要这样的转换时,编译器可以从语言语法中找出并发出所需的IL代码。

System.Int32类型是编译器具有特殊知识的辅助类型。它仅适用于其方法,您从不显式创建它的实例。当编译器知道你正在调用int“class”的方法时,它会直接调用这些方法。

所有这些一起工作来创建int派生自System.Object(通过System.ValueType)的错觉。使用“如果它看起来,像鸭子一样游泳和嘎嘎叫,它是一只鸭子”的原则。