Silverlight反编译系列二常见代码(自动生成属性CompilerGenerated,代码)

  在Silverlight有一些编译后自动生成的代码,最常见的是CompilerGeneratedAttribute和DebuggerNonUserCodeAttribute,下面介绍一下这俩种属性

1.CompilerGeneratedAttribute 自动属性

  使用自动属性后,你可以不用手工声明一个私有成员变量以及编写get/set逻辑,取而代之的是,编译器会自动为你生成一个私有变量和默认的get/set 操作。系统为你产生的私有变量在IDE中,你是看不到的,

如 public string ClassName { get; set; }

上面的代码我们编译后,再用 Reflector 反编译后,我们可以看到上述代码中的属性变成了如下代码:这个编译器给我们产生的私有变量,显然不是那么容易重名的。

 [CompilerGenerated]
    private string <ClassName>k__BackingField;

 

public string ClassName
    {
        [CompilerGenerated]
        get
        {
            return this.<ClassName>k__BackingField;
        }
        [CompilerGenerated]
        set
        {
            this.<ClassName>k__BackingField = value;
        }
    }

你可以看出private string <ClassName>k__BackingField中的ClassName是你定义的属性。编译系统会自动生成get,set方法。
注意:如果你只希望属性有 get 或者 set 方法,这些情况都是无法使用 自动属性的,需要你自己来书写。否则就会报如下的错误:

'ConsoleApplication1.MyClass.Name.set' must declare a body because it is not marked abstract or extern. Automatically implemented properties must define both get and set accessors.   

 

但是 get 和 set 访问级别不一样,比如一个是 public,一个是 internal,则可以书写成下述方式,而不会报错误。

public int ID { get; internal set; }

此类型一般都是(极少数除外)在类对应的Xaml中定义过的变量。因此也应该从源码文件中删掉。

使用自动属性后,你可以不用手工声明一个私有成员变量以及编写get/set逻辑,取而代之的是,编译器会自动为你生成一个私有变量和默认的get/set 操作。系统为你产生的私有变量在IDE中,你是看不到的,如下图:

当然如果你希望属性中有些赋值或者取值逻辑校验,自动属性可是不适合你的。

上面的代码我们编译后,再用 Reflector 反编译后,我们可以看到上述代码中的属性变成了如下代码:这个编译器给我们产生的私有变量,显然不是那么容易重名的。

[CompilerGenerated]
private string <>k__AutomaticallyGeneratedPropertyField0;

public string Name
{
    [CompilerGenerated]
    get
    {
        return this.<>k__AutomaticallyGeneratedPropertyField0;

    }
    [CompilerGenerated]
    set
    {
        this.<>k__AutomaticallyGeneratedPropertyField0 = value;
    }
}

注意:如果你只希望属性有 get 或者 set 方法,这些情况都是无法使用 自动属性的,需要你自己来书写。否则就会报如下的错误:

'ConsoleApplication1.MyClass.Name.set' must declare a body because it is not marked abstract or extern. Automatically implemented properties must define both get and set accessors.   

但是 get set 访问级别不一样,比如一个是 public,一个是 internal,则可以书写成下述方式,而不会报错误。

public int ID { get; internal set; }

  

2.DebuggerNonUserCodeAttribute 标识不属于应用程序用户代码的类型或成员。

  如果设计器提供的类型和成员不是由用户专门创建的代码的一部分,则会增加调试过程的复杂性。此特性禁止在调试器窗口中显示这些附属类型和成员,并自动逐句通过而不会进入并单步执行设计器提供的代码。当逐句通过用户代码时,如果调试器遇到此特性,用户将不会看到设计器提供的代码,并且会执行用户提供的下一条代码语句。

 [DebuggerNonUserCode]
    public void InitializeComponent()
    {
        if (!this._contentLoaded)
        {
            this._contentLoaded = true;
            Application.LoadComponent(this, new Uri("/ReflectorDemo;component/MainPage.xaml", UriKind.Relative));
            this.LayoutRoot = (Grid) base.FindName("LayoutRoot");
        }
    }
此段代码也是在程序编译后产生。

反编译后将此段代码从源文件中删掉。

3.上图中的private bool _contentLoaded;

 此类代码也是在程序编译后产生。

4.internal MediaElement xMedia1

修饰符为internal的变量一般都是(极少数除外)在类对应的Xaml中定义过的变量。因此也应该从源码文件中删掉。

posted @ 2010-09-20 10:23  ForrestWoo  阅读(9396)  评论(2编辑  收藏  举报