# C# 特性(Attribute)
**特性(Attribute)**是用于在運行時傳遞程序中各種元素(比如類、方法、結構、枚舉、組件等)的行為信息的聲明性標簽。您可以通過使用特性向程序添加聲明性信息。一個聲明性標簽是通過放置在它所應用的元素前面的方括號([ ])來描述的。
特性(Attribute)用于添加元數據,如編譯器指令和注釋、描述、方法、類等其他信息。.Net 框架提供了兩種類型的特性:_預定義_特性和_自定義_特性。
## 規定特性(Attribute)
規定特性(Attribute)的語法如下:
```
[attribute(positional_parameters, name_parameter = value, ...)]
element
```
特性(Attribute)的名稱和值是在方括號內規定的,放置在它所應用的元素之前。positional_parameters 規定必需的信息,name_parameter 規定可選的信息。
## 預定義特性(Attribute)
.Net 框架提供了三種預定義特性:
* AttributeUsage
* Conditional
* Obsolete
### AttributeUsage
預定義特性 **AttributeUsage** 描述了如何使用一個自定義特性類。它規定了特性可應用到的項目的類型。
規定該特性的語法如下:
```
[AttributeUsage(
validon,
AllowMultiple=allowmultiple,
Inherited=inherited
)]
```
其中:
* 參數 validon 規定特性可被放置的語言元素。它是枚舉器 _AttributeTargets_ 的值的組合。默認值是 _AttributeTargets.All_。
* 參數 _allowmultiple_(可選的)為該特性的 _AllowMultiple_ 屬性(property)提供一個布爾值。如果為 true,則該特性是多用的。默認值是 false(單用的)。
* 參數 _inherited_(可選的)為該特性的 _Inherited_ 屬性(property)提供一個布爾值。如果為 true,則該特性可被派生類繼承。默認值是 false(不被繼承)。
例如:
```
[AttributeUsage(AttributeTargets.Class |
AttributeTargets.Constructor |
AttributeTargets.Feild |
AttributeTargets.Method |
AttributeTargets.Property,
AllowMultiple = true)]
```
### Conditional
這個預定義特性標記了一個條件方法,其執行依賴于它頂的預處理標識符。
它會引起方法調用的條件編譯,取決于指定的值,比如 **Debug** 或 **Trace**。例如,當調試代碼時顯示變量的值。
規定該特性的語法如下:
```
[Conditional(
conditionalSymbol
)]
```
例如:
```
[Conditional("DEBUG")]
```
下面的實例演示了該特性:
```
#define DEBUG
using System;
using System.Diagnostics;
public class Myclass
{
[Conditional("DEBUG")]
public static void Message(string msg)
{
Console.WriteLine(msg);
}
}
class Test
{
static void function1()
{
Myclass.Message("In Function 1.");
function2();
}
static void function2()
{
Myclass.Message("In Function 2.");
}
public static void Main()
{
Myclass.Message("In Main function.");
function1();
Console.ReadKey();
}
}
```
當上面的代碼被編譯和執行時,它會產生下列結果:
```
In Main function
In Function 1
In Function 2
```
### Obsolete
這個預定義特性標記了不應被使用的程序實體。它可以讓您通知編譯器丟棄某個特定的目標元素。例如,當一個新方法被用在一個類中,但是您仍然想要保持類中的舊方法,您可以通過顯示一個應該使用新方法,而不是舊方法的消息,來把它標記為 obsolete(過時的)。
規定該特性的語法如下:
```
[Obsolete(
message
)]
[Obsolete(
message,
iserror
)]
```
其中:
* 參數 _message_,是一個字符串,描述項目為什么過時的原因以及該替代使用什么。
* 參數 _iserror_,是一個布爾值。如果該值為 true,編譯器應把該項目的使用當作一個錯誤。默認值是 false(編譯器生成一個警告)。
下面的實例演示了該特性:
```
using System;
public class MyClass
{
[Obsolete("Don't use OldMethod, use NewMethod instead", true)]
static void OldMethod()
{
Console.WriteLine("It is the old method");
}
static void NewMethod()
{
Console.WriteLine("It is the new method");
}
public static void Main()
{
OldMethod();
}
}
```
當您嘗試編譯該程序時,編譯器會給出一個錯誤消息說明:
```
Don't use OldMethod, use NewMethod instead
```
## 創建自定義特性(Attribute)
.Net 框架允許創建自定義特性,用于存儲聲明性的信息,且可在運行時被檢索。該信息根據設計標準和應用程序需要,可與任何目標元素相關。
創建并使用自定義特性包含四個步驟:
* 聲明自定義特性
* 構建自定義特性
* 在目標程序元素上應用自定義特性
* 通過反射訪問特性
最后一個步驟包含編寫一個簡單的程序來讀取元數據以便查找各種符號。元數據是用于描述其他數據的數據和信息。該程序應使用反射來在運行時訪問特性。我們將在下一章詳細討論這點。
### 聲明自定義特性
一個新的自定義特性應派生自 **System.Attribute** 類。例如:
```
// 一個自定義特性 BugFix 被賦給類及其成員
[AttributeUsage(AttributeTargets.Class |
AttributeTargets.Constructor |
AttributeTargets.Field |
AttributeTargets.Method |
AttributeTargets.Property,
AllowMultiple = true)]
public class DeBugInfo : System.Attribute
```
在上面的代碼中,我們已經聲明了一個名為 _DeBugInfo_ 的自定義特性。
### 構建自定義特性
讓我們構建一個名為 _DeBugInfo_ 的自定義特性,該特性將存儲調試程序獲得的信息。它存儲下面的信息:
* bug 的代碼編號
* 辨認該 bug 的開發人員名字
* 最后一次審查該代碼的日期
* 一個存儲了開發人員標記的字符串消息
我們的 _DeBugInfo_ 類將帶有三個用于存儲前三個信息的私有屬性(property)和一個用于存儲消息的公有屬性(property)。所以 bug 編號、開發人員名字和審查日期將是 DeBugInfo 類的必需的定位( positional)參數,消息將是一個可選的命名(named)參數。
每個特性必須至少有一個構造函數。必需的定位( positional)參數應通過構造函數傳遞。下面的代碼演示了 _DeBugInfo_ 類:
```
// 一個自定義特性 BugFix 被賦給類及其成員
[AttributeUsage(AttributeTargets.Class |
AttributeTargets.Constructor |
AttributeTargets.Field |
AttributeTargets.Method |
AttributeTargets.Property,
AllowMultiple = true)]
public class DeBugInfo : System.Attribute
{
private int bugNo;
private string developer;
private string lastReview;
public string message;
public DeBugInfo(int bg, string dev, string d)
{
this.bugNo = bg;
this.developer = dev;
this.lastReview = d;
}
public int BugNo
{
get
{
return bugNo;
}
}
public string Developer
{
get
{
return developer;
}
}
public string LastReview
{
get
{
return lastReview;
}
}
public string Message
{
get
{
return message;
}
set
{
message = value;
}
}
}
```
### 應用自定義特性
通過把特性放置在緊接著它的目標之前,來應用該特性:
```
[DeBugInfo(45, "Zara Ali", "12/8/2012", Message = "Return type mismatch")]
[DeBugInfo(49, "Nuha Ali", "10/10/2012", Message = "Unused variable")]
class Rectangle
{
// 成員變量
protected double length;
protected double width;
public Rectangle(double l, double w)
{
length = l;
width = w;
}
[DeBugInfo(55, "Zara Ali", "19/10/2012",
Message = "Return type mismatch")]
public double GetArea()
{
return length * width;
}
[DeBugInfo(56, "Zara Ali", "19/10/2012")]
public void Display()
{
Console.WriteLine("Length: {0}", length);
Console.WriteLine("Width: {0}", width);
Console.WriteLine("Area: {0}", GetArea());
}
}
```
在下一章中,我們將使用 Reflection 類對象來檢索這些信息。
- C# 基礎
- C# 簡介
- C# 環境
- C# 程序結構
- C# 基本語法
- C# 數據類型
- C# 類型轉換
- C# 變量
- C# 常量
- C# 運算符
- C# 判斷
- C# 循環
- C# 封裝
- C# 方法
- C# 可空類型(Nullable)
- C# 數組(Array)
- C# 字符串(String)
- C# 結構(Struct)
- C# 枚舉(Enum)
- C# 類(Class)
- C# 繼承
- C# 多態性
- C# 運算符重載
- C# 接口(Interface)
- C# 命名空間(Namespace)
- C# 預處理器指令
- C# 正則表達式
- C# 異常處理
- C# 文件的輸入與輸出
- C# 高級
- C# 特性(Attribute)
- C# 反射(Reflection)
- C# 屬性(Property)
- C# 索引器(Indexer)
- C# 委托(Delegate)
- C# 事件(Event)
- C# 集合(Collection)
- C# 泛型(Generic)
- C# 匿名方法
- C# 不安全代碼
- C# 多線程
- ASP.NET 簡介
- Web Pages 教程
- ASP.NET Web Pages - 教程
- ASP.NET Web Pages - 添加 Razor 代碼
- ASP.NET Web Pages - 頁面布局
- ASP.NET Web Pages - 文件夾
- ASP.NET Web Pages - 全局頁面
- ASP.NET Web Pages - HTML 表單
- ASP.NET Web Pages - 對象
- ASP.NET Web Pages - 文件
- ASP.NET Web Pages - 幫助器
- ASP.NET Web Pages - WebGrid 幫助器
- ASP.NET Web Pages - Chart 幫助器
- ASP.NET Web Pages - WebMail 幫助器
- ASP.NET Web Pages - PHP
- ASP.NET Web Pages - 發布網站
- Razor 教程
- ASP.NET Razor - 標記
- ASP.NET Razor - C# 和 VB 代碼語法
- ASP.NET Razor - C# 變量
- ASP.NET Razor - C# 循環和數組
- ASP.NET Razor - C# 邏輯條件
- ASP.NET Razor - VB 變量
- ASP.NET Razor - VB 循環和數組
- ASP.NET Razor - VB 邏輯條件
- MVC 教程
- ASP.NET MVC 教程
- ASP.NET MVC - Internet 應用程序
- ASP.NET MVC - 應用程序文件夾
- ASP.NET MVC - 樣式和布局
- ASP.NET MVC - 控制器
- ASP.NET MVC - 視圖
- ASP.NET MVC - SQL 數據庫
- ASP.NET MVC - 模型
- ASP.NET MVC - 安全
- ASP.NET MVC - HTML 幫助器
- ASP.NET MVC - 發布網站
- Web Forms 教程
- ASP.NET Web Forms - 教程
- ASP.NET Web Forms - HTML 頁面
- ASP.NET Web Forms - 服務器控件
- ASP.NET Web Forms - 事件
- ASP.NET Web Forms - HTML 表單
- ASP.NET Web Forms - 維持 ViewState
- ASP.NET Web Forms - TextBox 控件
- ASP.NET Web Forms - Button 控件
- ASP.NET Web Forms - 數據綁定
- ASP.NET Web Forms - ArrayList 對象
- ASP.NET Web Forms - Hashtable 對象
- ASP.NET Web Forms - SortedList 對象
- ASP.NET Web Forms - XML 文件
- ASP.NET Web Forms - Repeater 控件
- ASP.NET Web Forms - DataList 控件
- ASP.NET Web Forms - 數據庫連接
- ASP.NET Web Forms - 母版頁
- ASP.NET Web Forms - 導航
- Web Pages 參考手冊
- ASP.NET Web Pages - 類
- ASP.NET Web Pages - WebSecurity 對象
- ASP.NET Web Pages - Database 對象
- ASP.NET Web Pages - WebMail 對象
- ASP.NET Web Pages - 更多幫助器
- MVC - 參考手冊
- Web Forms 參考手冊
- ASP.NET Web Forms - HTML 服務器控件
- ASP.NET Web Forms - Web 服務器控件
- ASP.NET Web Forms - Validation 服務器控件
- 免責聲明