ConditionalAttribute 告訴 C# 編譯器:此方法僅在編譯環境變數 DEBUG 定義時才被呼叫。同時,它不影響 CheckState() 產生的程式碼,僅修改對方法的呼叫。若定義 DEBUG,屬性存取器會保留呼叫;否則呼叫被移除:
// DEBUG 定義時
public string LastName
{
get { CheckState(); return _lastName; }
set { CheckState(); _lastName = value; CheckState(); }
}
// DEBUG 未定義時
public string LastName
{
get { return _lastName; }
set { _lastName = value; }
}
無論環境變數狀態,CheckState() 方法本體總會被編譯並存在於組件中。這看似低效,但僅佔少量磁碟空間;除非被呼叫,否則不會載入記憶體,更不會被 JIT 編譯為機器碼。這策略增強程式擴充性,效能開銷微乎其微。.NET Framework 的 System.Diagnostics.Debug 類別即採此策略:System.dll 包含所有方法程式碼,由環境變數決定編譯時是否呼叫。
可套用多個 ConditionalAttribute,呈 OR 關係:
[Conditional("DEBUG"), Conditional("TRACE")]
private void CheckState() { ... }
若需 AND 關係,須先用預處理器定義新符號:
#if (VAR1 && VAR2)
#define BOTH
#endif
void 的方法實體,不可用於程式碼區塊或有回傳值的方法。#if/#endif 更好:避免錯誤移除重要呼叫,強制結構更佳,編譯器協助避免常見錯誤。書中範例略顯冗餘,但 ConditionalAttribute 確實提供更優雅的條件式編譯方式,值得掌握。