代码之家  ›  专栏  ›  技术社区  ›  Mike

如何在.NET中实现值类型

  •  4
  • Mike  · 技术社区  · 16 年前

    一直在网上搜索,找不到任何关于值类型是如何实际实现的文章。

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

    什么是类层次结构?CLR必须扮演什么角色?CLR在什么阶段以及如何知道向堆栈分配值类型(仅供参考,我知道值类型存储在声明它们的位置)。

    3 回复  |  直到 16 年前
        1
  •  1
  •   Hans Passant    16 年前

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

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

    如果你有一个好的.NET编译器,比如C#编译器,你永远不会自己显式调用转换。编译器可以从语言语法中找出何时需要这种转换,并发出所需的IL代码。

    System.Int32类型是一种帮助程序类型,编译器对此有专门的知识。它只对它的方法有用,您从不显式地创建它的实例。当编译器知道您正在调用int“class”的方法时,它会直接调用这些方法。

    所有这一切共同创造了int从System.Object(通过System.ValueType)派生的假象。运用“如果它看起来、游泳、嘎嘎叫得像鸭子,那就是鸭子”的原则。

        2
  •  1
  •   Marcelo Cantos    16 年前

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

    我不知道如果不进入“实现定义”的领域,还能说多少关于值类型的话。

        3
  •  1
  •   EMP    16 年前

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

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

    推荐文章