Attribute在.net程式設計中的應用(一) (轉)
Attribute在中的應用(一)
Attribute的基本概念
經常有朋友問,Attribute是什麼?它有什麼用?好像沒有這個東東也能執行。實際上在.Net中,Attribute是一個非常重要的組成部分,為了幫助大家理解和掌握Attribute,以及它的使用方法,特地收集了幾個Attribute使用的例子,提供給大家參考。
在具體的演示之前,我想先大致介紹一下Attribute。我們知道在類的成員中有property成員,二者在中文中都做屬性解釋,那麼它們到底是不是同一個東西呢?從程式碼上看,明顯不同,首先就是它們的在程式碼中的位置不同,其次就是寫法不同(Attribute必須寫在一對方括符中)。
什麼是Atrribute
首先,我們肯定Attribute是一個類,下面是msdn文件對它的描述:
公共語言執行時允許你新增類似關鍵字的描述宣告,叫做attributes, 它對程式中的元素進行標註,如型別、欄位、方法和屬性等。Attributes和 的後設資料儲存在一起,可以用來向執行時描述你的程式碼,或者在程式執行的時候影響應用程式的行為。
在.NET中,Attribute被用來處理多種問題,比如序列化、程式的特徵、防止即時對程式程式碼進行從而程式碼容易等等。下面,我們先來看幾個在.NET中標準的屬性的使用,稍後我們再回過頭來討論Attribute這個類本身。(文中的程式碼使用編寫,但同樣適用所有基於.NET的所有語言)
Attribute作為編譯器的指令
在C#中存在著一定數量的編譯器指令,如:#define DE, #undefine DEBUG, #if等。這些指令專屬於C#,而且在數量上是固定的。而Attribute用作編譯器指令則不受數量限制。比如下面的三個Attribute:
- Conditional:起條件編譯的作用,只有滿足條件,才允許編譯器對它的程式碼進行編譯。一般在程式除錯的時候使用。
- DllImport:用來標記非.NET的,表明該方法在一個外部的DLL中定義。
- Obsolete:這個屬性用來標記當前的方法已經被廢棄,不再使用了。
下面的程式碼演示了上述三個屬性的使用:
#define DEBUG //這裡定義條件 using System; using System.Runtime.InteropServices; using System.Diagnostics; namespace AttributeDemo { class MainProgramClass { [DllImport("User32.dll")] public static extern int MessageBox(int hParent, string Message, string Caption, int Type); static void Main(string[] args) { DisplayRunningMessage(); DisplayDebugMessage(); MessageBox(0,"Hello","Message",0); Console.ReadLine(); } [Conditional("DEBUG")] private static void DisplayRunningMessage() { Console.WriteLine("開始執行Main子程式。當前時間是"+DateTime.Now); } [Conditional("DEBUG")] [Obsolete] private static void DisplayDebugMessage() { Console.WriteLine("開始Main子程式"); } } }
如果在一個程式元素前面宣告一個Attribute,那麼就表示這個Attribute被施加到該元素上,前面的程式碼,[DllImport]施加到MessageBox函式上, [Conditional]施加到DisplayRuntimeMessage方法和DisplayDebugMessage方法,[Obsolete]施加到DisplayDebugMessage方法上。
根據上面涉及到的三個Attribute的說明,我們可以猜到程式執行的時候產生的輸出:DllImport Attribute表明了MessageBox是User32.DLL中的函式,這樣我們就可以像內部方法一樣這個函式。
重要的一點就是Attribute就是一個類,所以DllImport也是一個類,Attribute類是在編譯的時候被例項化的,而不是像通常的類那樣在執行時候才例項化。Attribute例項化的時候根據該Attribute類的設計可以帶引數,也可以不帶引數,比如DllImport就帶有"User32.dll"的引數。Conditional對滿足引數的定義條件的程式碼進行編譯,如果沒有定義DEBUG,那麼該方法將不被編譯,讀者可以把#define DEBUG一行註釋掉看看輸出的結果(release版本,在Debug版本中Conditional的debug總是成立的)。Obsolete表明了DispalyDebugMessage方法已經過時了,它有一個更好的方法來代替它,當我們的程式呼叫一個宣告瞭Obsolete的方法時,那麼編譯器會給出資訊,Obsolete還有其他兩個過載的版本。大家可以參考msdn中關於的ObsoleteAttribute 類的描述。
Attribute類
除了.NET提供的那些Attribute派生類之外,我們可以自定義我們自己的Attribute,所有自定義的Attribute必須從Attribute類派生。現在我們來看一下Attribute 類的細節:
protected Attribute(): 保護的構造器,只能被Attribute的派生類呼叫。
三個靜態方法:
static Attribute GetCustomAttribute():這個方法有8種過載的版本,它被用來取出施加在類成員上指定型別的Attribute。
static Attribute[] GetCustomAttributes(): 這個方法有16種過載版本,用來取出施加在類成員上指定型別的Attribute陣列。
static bool IsDefined():由八種過載版本,看是否指定型別的定製attribute被施加到類的成員上面。
例項方法:
bool IsDefaultAttribute(): 如果Attribute的值是預設的值,那麼返回true。
bool Match():表明這個Attribute例項是否等於一個指定的。
公共屬性: TypeId: 得到一個唯一的標識,這個標識被用來區分同一個Attribute的不同例項。
我們簡單地介紹了Attribute類的方法和屬性,還有一些是從繼承來的。這裡就不列出來了。
下面介紹如何自定義一個Attribute: 自定義一個Attribute並不需要特別的知識,其實就和編寫一個類差不多。自定義的Attribute必須直接或者間接地從Attribute這個類派生,如:
public MyCustomAttribute : Attribute { ... }
這裡需要指出的是Attribute的命名規範,也就是你的Attribute的類名+"Attribute",當你的Attribute施加到一個程式的元素上的時候,編譯器先查詢你的Attribute的定義,如果沒有找到,那麼它就會查詢“Attribute名稱"+Attribute的定義。如果都沒有找到,那麼編譯器就報錯。
對於一個自定義的Attribute,你可以透過AttributeUsage的Attribute來限定你的Attribute 所施加的元素的型別。程式碼形式如下: [AttriubteUsage(引數設定)] public 自定義Attribute : Attribute { ... }
非常有意思的是,AttributeUsage本身也是一個Attribute,這是專門施加在Attribute類的Attribute. AttributeUsage自然也是從Attribute派生,它有一個帶引數的構造器,這個引數是AttributeTargets的列舉型別。下面是AttributeTargets 的定義:
public enum AttributeTargets { All=16383, Assembly=1, Module=2, Class=4, Struct=8, Enum=16, Constructor=32, Method=64, Property=128, Field=256, Event=512, Interface=1024, Parameter=2048, Delegate=4096, ReturnValue=8192 }
作為引數的AttributeTarges的值允許透過“或”操作來進行多個值得組合,如果你沒有指定引數,那麼預設引數就是All 。 AttributeUsage除了繼承Attribute 的方法和屬性之外,還定義了以下三個屬性:
AllowMultiple: 讀取或者設定這個屬性,表示是否可以對一個程式元素施加多個Attribute 。
Inherited:讀取或者設定這個屬性,表示是否施加的Attribute 可以被派生類繼承或者過載。
ValidOn: 讀取或者設定這個屬性,指明Attribute 可以被施加的元素的型別。
AttributeUsage 的使用例子:
using System; namespace AttTargsCS { // 該Attribute只對類有效. [AttributeUsage(AttributeTargets.Class)] public class ClassTargetAttribute : Attribute { } // 該Attribute只對方法有效. [AttributeUsage(AttributeTargets.Method)] public class MethodTargetAttribute : Attribute { } // 該Attribute只對構造器有效。 [AttributeUsage(AttributeTargets.Constructor)] public class ConstructorTargetAttribute : Attribute { } // 該Attribute只對欄位有效. [AttributeUsage(AttributeTargets.Field)] public class FieldTargetAttribute : Attribute { } // 該Attribute對類或者方法有效(組合). [AttributeUsage(AttributeTargets.Class|AttributeTargets.Method)] public class ClassMethodTargetAttribute : Attribute { } // 該Attribute對所有的元素有效. [AttributeUsage(AttributeTargets.All)] public class AllTargetsAttribute : Attribute { } //上面定義的Attribute施加到程式元素上的用法 [ClassTarget] //施加到類 [ClassMethodTarget]//施加到類 [AllTargets] //施加到類 public class TestClassAttribute { [ConstructorTarget] //施加到構造器 [AllTargets] //施加到構造器 TestClassAttribute() { } [MethodTarget] //施加到方法 [ClassMethodTarget] //施加到方法 [AllTargets] //施加到方法 public void Method1() { } [FieldTarget] //施加到欄位 [AllTargets] //施加到欄位 public int myInt; static void Main(string[] args) { } } }
至此,我們介紹了有關Attribute類和它們的程式碼格式。你一定想知道到底如何在你的應用程式中使用Attribute,如果僅僅是前面介紹的內容,還是不足以說明Attribute有什麼實用價值的話,那麼從後面的章節開始我們將介紹幾個Attribute的不同用法,相信你一定會對Attribute有一個新的瞭解。(待續)
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/10752019/viewspace-982736/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- Attribute 在.NET程式設計中的應用(二) (轉)程式設計
- Attribute在.NET程式設計中的應用(四) (轉)程式設計
- Attribute在.NET程式設計中的應用(五) (轉)程式設計
- Attribute在.NET程式設計中的應用(三) (轉)程式設計
- Attribute在.NET程式設計的應用(六) (轉)程式設計
- Vector在Java程式設計中的應用 (轉)Java程式設計
- socket程式設計在TCP中的應用程式設計TCP
- 設計模式在vue中的應用(一)設計模式Vue
- .NET Attribute在資料校驗上的應用
- [譯] 設計 QA 在應用程式設計中的重要性程式設計
- .Net 中的反應式程式設計程式設計
- 在ASP.NET中物件導向的程式設計思想 (轉)ASP.NET物件程式設計
- 從一個問題中瞭解數學在程式設計中的應用程式設計
- 雙緩衝在畫板程式中的應用(一) (轉)
- 用例設計在軟體開發專案計劃中的應用(轉)
- 函數語言程式設計及其在react中的應用函數程式設計React
- 設計模式及其在spring中的應用(含程式碼)設計模式Spring
- 設計模式在vue中的應用(六)設計模式Vue
- 設計模式在vue中的應用(七)設計模式Vue
- 設計模式在vue中的應用(五)設計模式Vue
- 設計模式在vue中的應用(三)設計模式Vue
- 設計模式在vue中的應用(四)設計模式Vue
- 設計模式在vue中的應用(二)設計模式Vue
- 設計模式,及在Java中的應用設計模式Java
- union 的概念及在嵌入式程式設計中的應用程式設計
- 關於分散式鎖在程式設計中的一些應用場景分散式程式設計
- State模式在J2ME遊戲設計中的應用(轉)模式遊戲設計
- 非Access資料庫在VB的程式設計及應用 (轉)資料庫程式設計
- ADO程式設計應用 (轉)程式設計
- .net core 中的經典設計模式的應用設計模式
- GlusterFS在Kubernetes中的應用實戰(一)
- 聯合體在微控制器程式設計中的應用程式設計
- 設計模式在 TypeScript 中的應用 – 策略模式設計模式TypeScript
- IR在IS需求分析與設計中的應用
- 在netweaver中建立應用程式客戶端客戶端
- .NET應用程式管理服務AMS設計
- 響應式程式設計在Android 中的一些探索程式設計Android
- AOP程式設計之AspectJ介紹及在Android中的應用程式設計Android