MSIL 初级读本 第三部分:定义类型
这一次,让我们来看看如何在 MSIL 中定义类型。下面是一个叫做 House 的最简单的引用类型:
请注意,必须为具体的引用类型声明一个构造函数。这一点并不像 C# 或者 C++,IL 编译器不会为你自动生成一个构造函数。
MSIL 使用 .class 指示符加上类型头部来定义一个类型。类型头部包括一些类型修饰符以及类型名称。要定义C# 中静态类的等价物,应当使用类似如下代码:
abstract 和 sealed 是类型修饰符。被 abstract 修饰的抽象类,无法实例化,而被 sealed 修饰的密封类无法作为其他类的基类。此外还有控制可见性的修饰符如,public 和 private;控制字段布局的修饰符如,auto 和 sequential。有关修饰符的完整列表请参考 CLI 规范。很多修饰符都是默认存在的,这将简化代码的输入。一般情况下,这种缺省修饰符是很直观的。例如,继承 mscorlib 程序及中的 System.ValueType 类会定义一个值类型,由于 CLI 要求值类型必须是密封的,IL 会自动添加 sealed 修饰符。
上一个例子中定义的类,名称是 Kerr.RealEstate.MortgageCalculator。在这里 CIL 并不知道其命名空间,而是一直使用 Kerr.RealEstate.MortgageCalculator 这一完整名称。而且此语法仅在 .NET Framework 2.0 提供的编译器中可以使用。如果工作于此前的版本上,你需要使用 .namespace 指示符来组织命名空间的成员。当然,下面的语法在 2.0 中也是受到支持的。
在类名称之后你可以使用 extends 关键字来指定一个基类。如果没有指定任何基类 IL 编译器会自动添加继承自 System.Object 类的语句,这使得定义的类型成为一个引用类型。最后,在类型的头部可以给出一个该类型及其派生类必须实现的接口列表。
在上面的例子中, Kerr.RealEstate.RoomList 以 System.Windows.Forms.ListView 为基类,后者定义在 System.Windows.Forms 程序集中。CLI 仅支持单根继承。RoomList 类还实现了 Kerr.IView 接口。
要定义接口类型仅需在类型头部中添加 interface 修饰符。要获得自定义的值类型,即 C# 中的 struct 结构,仅需继承 mscorlib 程序集中的 System.ValueType 类。