天天看點

反射和屬性

?反射的概念

?反射周遊成員

?用射調用類型成員

?屬性概念(Attribute)

?屬性的執行個體

?自定議屬性

?三個屬性

二次編輯一次運作

<a href="http://axzxs.blog.51cto.com/attachment/200907/17/730810_1247794197usOt.jpg"></a>

一次編譯後

<a href="http://axzxs.blog.51cto.com/attachment/200907/17/730810_1247794201X5IE.jpg"></a>

反射

反射是程式設計的讀取與類型相關聯的中繼資料的行為。通讀取中繼資料,可以了解它是什麼類型以及類型的成員。比如類中的屬性,方法,事件等。

所屬命名空間System.Reflection

反射-反射成員名稱

class Demo_Class

{

public Demo_Class(int i)

Console.WriteLine("構造函數:" + i);

}

public void Method(string s)

Console.WriteLine("A類參數為:" + s);

public int i;

public string S

get; set;

調用

static void Main(string[] args)

Type type = typeof(Demo_Class);

MemberInfo[] MI = type.GetMembers(BindingFlags.NonPublic | BindingFlags.Public |BindingFlags .Instance );

foreach (MemberInfo mi in MI)

Console.WriteLine("名稱:{0},類型:{1}",mi.Name,mi.MemberType .ToString ());

運作結果

<a href="http://axzxs.blog.51cto.com/attachment/200907/17/730810_1247794219U5Uk.png"></a>

反射-用反射調用無參構造類型成員

class Program

BindingFlags bf = BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance;

Type t = typeof(Demo_Class);

ConstructorInfo Cons = t.GetConstructor(new Type[0]); //構造函數無參,是以構造函數無類型參數

object Obj = Cons.Invoke(null);//傳入的構造參數為空,得到對象

object[] MethodPar = new object[] { “a” }; //方法的參數

MethodInfo mi = t.GetMethod(“Method”, bf);//得到方法

Console.WriteLine(mi.Invoke(Obj, MethodPar));

反射-用反射調用有參構造類型成員

ConstructorInfo Cons = t.GetConstructor(new Type[]{typeof(int)}); //構造函數有參,類型為int

object Obj = Cons.Invoke(net object[]{123});//傳入的構造參數, 得到對象

屬性-Attribute

Attribute非property(類的成員)

屬性提供功能強大的方法以将聲明資訊與 C# 代碼(類型、方法、屬性等)相關聯。

屬性與程式實體關聯後,即可在運作時使用名為“反射”的技術查詢屬性。

屬性以兩種形式出現:

1.一種是在公共語言運作庫 (CLR) 中定義的屬性。

2.另一種是可以建立的用于向代碼中添加附加資訊的自定義屬性。此資訊可在以後以程式設計方式檢索。

屬性具有以下特點:

1.屬性可向程式中添加中繼資料。中繼資料是嵌入程式中的資訊,如編譯器指令或資料描述。

2.程式可以使用反射檢查自己的中繼資料。

3.通常使用屬性與 COM 互動。

一個例子:

[System.Runtime.InteropServices.DllImportAttribute("user32.dll", EntryPoint = "MessageBoxW")]

public static extern int MessageBoxW([System.Runtime.InteropServices.InAttribute()] System.IntPtr hWnd, [System.Runtime.InteropServices.InAttribute()] [System.Runtime.InteropServices.MarshalAsAttribute(System.Runtime.InteropServices.UnmanagedType.LPWStr)] string lpText, [System.Runtime.InteropServices.InAttribute()] [System.Runtime.InteropServices.MarshalAsAttribute(System.Runtime.InteropServices.UnmanagedType.LPWStr)] string lpCaption, uint uType);

Console .WriteLine ( MessageBoxW(IntPtr .Zero , "确定嗎?", "提示",1));

自定義屬性

通過定義一個屬性類,可以建立您自己的自定義屬性。該屬性類直接或間接地從System. Attribute 派生,有助于友善快捷地在中繼資料中辨別屬性定義。假設您要用編寫類或結構的程式員的名字标記類和結構。

[System.AttributeUsage(System.AttributeTargets.Class | System.AttributeTargets.Struct,AllowMultiple=true ,Inherited =true ) ] //Author屬性隻能用于類和結構,AllowMultiple是否允許多次用屬性,Inherited是這個屬性是滞延續到子類。

public class Author : System.Attribute

private string name;

public double version;

public Author(string name)

this.name = name; version = 1.0;

[Author(“張三”, version =2.0)]//張三是Author的構造函數的參數,version是字段

class SampleClass

{ }

三個特别的屬性

1.AttributeUsage屬性(上面的例子已經示範)

2.Conditional屬性

3.Obsolete屬性

三個特别的屬性- Conditional

條件方法必須是類或結構聲明中的方法,而且必須具有 void 傳回類型。

#define TRACE_ON //這行辨別代碼決定着紅色代碼的執行與否。

using System;

using System.Diagnostics;

namespace R_A_Demo

public class Trace

[Conditional("TRACE_ON")]

public static void Msg(string msg)

Console.WriteLine(msg);

public class ProgramClass

static void Main()

Trace.Msg(“調試資訊”);

Console.WriteLine(“代碼正體");

另一種用法

#define TRACE_ON

#if TRACE_ON

#endif

Trace.Msg("Now in Main...");

Console.WriteLine("Done.");

三個特别的屬性- Obsolete

[System.Obsolete("use class B")] //類會被在執行個體化時警告

class A

public void Method() { }

class B

[System.Obsolete("use NewMethod", false )] //方法調用時提示資訊

public void OldMethod() { }

[System.Obsolete("use NewMethod", true)] //不可編譯

public void NewMethod() { }

一句話總結:

反射:利用一次編譯後的結果,反得到類型和類型成員。

屬性(Attribute):額外給其他類型添加資訊的類型。

本文轉自桂素偉51CTO部落格,原文連結:http://blog.51cto.com/axzxs/179346 ,如需轉載請自行聯系原作者