之前看過不少關於C# 3.0的自動實作屬性(Auto-Implemented Properties)特性介紹,但看過好幾篇文章都是只提了類似以下的例子:

使用前:

private int _length = 0;
public int Length
{
    get { return _length; }
    set { _length = value; }
}

使用後:

public int Length { get; set; }

號稱是四行變一行,但我心中一直有個疑惑,要這麼搞,何不直接來個:

public int Length = 0;

更是乾脆痛快,還少打好幾個字。Property比直接宣告公開變數的優勢是可以指定成唯讀或唯寫及加上客製邏輯,若對外完全開放讀寫又不打算加工,何必脫了褲子放屁包成Property?

今天在Coding時,一時興起也想用一下C# 3.0的新功能,而這次的屬性想設成唯讀,就試了以下的寫法:

public int Length { get; }

才寫完自己就覺得不對勁。靠腰! 只有get,那不是連自己的Code也沒法設定它的值? 果然,一Build就得到以下的錯誤

'My.WebControl.MyProp.get' must declare a body because it is not marked abstract or extern. Automatically implemented properties must define both get and set accessors.

get與set要成對出現? 那豈不跟直接宣告公開變數沒兩樣? 不過,用錯誤訊息Google到相關文章,終於了解到它真正的好處。對外唯讀時要寫成這樣:

public int Length { get; private set; }

原來MSDN Libary早有明確的介紹,get, set前只要加上Access Modifier(例如: private, internal, protected...)就可以管控讀寫的範圍,如此便比傳統寫法省事許多,這才是它的犀利之處。只能怪先前運氣不好,看過的幾篇文件都沒點到關鍵,自己又不求甚解,沒認真找答案。

我猜也許會有人跟我一樣,這份心得就跟大家報告一下囉。


Comments

# by sholfen

沒錯沒錯,我之前也是跟你一樣想法,直接將data member設為public,不但省事而且效率也較好,用Property會讓效能差一些些,因為它其實是class 裡面的method,後來才知道可以各別對get及set設定權限。

# by 效能狂

小弟我就是那個不求甚解的懶人, 我學陶淵明的。 感謝大大的分享。 http://blog.xuite.net/j2ee/coder

# by ooXx

VBer 有點痛苦 每每都要打滿很多行才有此效果.... 我想 VB Team 可能是不鼓勵 Programmer 在 Class 裡加入太多 Property 吧.................= ________ =;;

# by mOMo

如果用舊寫法可以用 if (value > 99) //statement 那如果用新寫法 public int GetOld { get; set; } 要從何實作呢?要用舊寫法是嗎? ^_^

# by mOMo

舊寫法可使用 if (value > 99) //statement 新寫法public int Length { get; set; } 有別種斷判方法嗎?還是要使用舊寫呢? ^_^

# by Jeffrey

to mOMo, 依官方文件的說法 Auto-implemented properties make property-declaration more concise when "no additional logic is required" in the property accessors. 因此若想加上額外的邏輯,就要回歸到傳統寫法囉。

# by 曉婷

Hello: public int Length { get; private set; } 這方法是只適用在C# 3.0嗎?

# by Jeffrey

to 曉婷, 是的,C# 3.0起開始支援。In C# 3.0 and later, auto-implemented properties make property-declaration more concise when no additional logic is required in the property accessors. http://msdn.microsoft.com/en-us/library/bb384054.aspx

# by 吉格艾諾

「可存取範圍」在程式設計領域本來就是很基本的觀念吧?不需要講到現在的物件導向程式,這種機制早在 VB6 那個時代就已經有了。個人認為,這已經不是什麼不求甚解的問題,我很好奇您是不是科班出身的。

# by Alex

不小心google到這篇四年前的文章解了我的大疑問,感謝大大!

# by 安安

現在public int Length { get; }這種寫法也已經可以用拉 重點你還是沒解釋到若我根本沒有要設定權限 ,為啥要額外封裝

# by Jeffrey

to 安安, 沒有要設定權限 ,為啥要額外封裝 <= 是指何不 public int Length = 0; 就好,要寫成 public int Length { get; set; } 嗎? 前者是 Field,後者是 Property,有些邏輯如 JSON 序列化時會略過 Field 只處理 Property,宣告成 Field 或 Property 便有差別。

Post a comment