MSIL 初级读本 第三部分:定义类型

   
声明:本文译自 Kenny Kerr 的 blog,共有 8 篇。如果大家有更好的 MSIL 入门文章也欢迎推荐,谢谢。



    这一次,让我们来看看如何在 MSIL 中定义类型。下面是一个叫做 House 的最简单的引用类型:
       

   

.class Kerr.RealEstate.House
{
    .method public void .ctor()
    {
        .maxstack 1
       
        ldarg.0 // 将 this 对象的引用压栈
        call instance void [mscorlib]System.Object::.ctor()
       
        ret
    }
}


    
    请注意,必须为具体的引用类型声明一个构造函数。这一点并不像 C# 或者 C++,IL 编译器不会为你自动生成一个构造函数。
MSIL 使用 .class 指示符加上类型头部来定义一个类型。类型头部包括一些类型修饰符以及类型名称。要定义C# 中静态类的等价物,应当使用类似如下代码:
   

   
.class abstract sealed Kerr.RealEstate.MortgageCalculator
{
    /* members */
}

 

    abstractsealed 是类型修饰符。被 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 中也是受到支持的。
   

   
.namespace Kerr.RealEstate
{
    .class abstract sealed MortgageCalculator
    {
        /* members */
    }
}

 

    在类名称之后你可以使用 extends 关键字来指定一个基类。如果没有指定任何基类 IL 编译器会自动添加继承自 System.Object 类的语句,这使得定义的类型成为一个引用类型。最后,在类型的头部可以给出一个该类型及其派生类必须实现的接口列表。

   
.class Kerr.RealEstate.RoomList
    extends [System.Windows.Forms]System.Windows.Forms.ListView
    implements Kerr.IView
{
    /* members */
}


    在上面的例子中, Kerr.RealEstate.RoomList 以 System.Windows.Forms.ListView 为基类,后者定义在 System.Windows.Forms 程序集中。CLI 仅支持单根继承。RoomList 类还实现了 Kerr.IView 接口。

    要定义接口类型仅需在类型头部中添加 interface 修饰符。要获得自定义的值类型,即 C# 中的 struct 结构,仅需继承 mscorlib 程序集中的 System.ValueType 类。

   
.class interface Kerr.IView
{
    /* members */
}

.class Kerr.RealEstate.HouseData
    extends [mscorlib]System.ValueType
{
    /* members */
}

posted on 2005-02-05 22:36  勇者之心  阅读(755)  评论(0编辑  收藏  举报