免費論壇 繁體 | 簡體
Sclub交友聊天~加入聊天室當版主
分享
Board logo

標題: VB.net入門(10):補充:類~屬性 [打印本頁]

作者: mhfo    時間: 2013-5-20 08:21     標題: VB.net入門(10):補充:類~屬性

原文出處

剛剛發現類還沒有寫完,還有一個比較大的部分:屬性(Property)。

Property在Java和C++裡面都是聞所未聞的。通常認為類當中只要有成員和方法就行了。至於屬性呢,當使用的時候,屬性看起來就像成員,屬性和成員有很多相似之處。但是屬性有更多獨特之處,它可以說是VB的一大特色。我的理解就是屬性是為了更好的對成員進行處理而存在的。

屬性是這樣一種東西,它看起來像是成員,但本質上它是函數。屬性的定義是這樣的:
public property MyProperty() as Object 'MyProperty是屬性的名字
Get '這個地方不能打括號
return mvarMyProperty
end Get

Set(Byval Value as Object)
mvarMyProperty = Value
end Set
end Property

可以看到,屬性其實是由兩個函數組成的:Get 和 Set()。當我們讀取屬性的時候,它就調用Get,所以Get裡面必須有return語句;當設置屬性的時候,它就調用Set(),所以Set()是帶參數的。當外界讀取MyProperty的時候,MyProperty就返回mvarMyProperty。mvarMyProperty是事先聲明好的變量。當外界設置MyProperty的時候,所賦的值就賦給mvarMyProperty。在這裡,mvar-是VB6中缺省使用的前綴,表明這是一個存放屬性的變量。

到這裡你可能理解了,屬性本身不保存數據,它通過另一個變量來讀寫。但是這又是一件奇怪的事:有必要這麼麻煩嗎?我直接寫:
public MyProperty As Object

不是更簡單嗎?
這裡有一個簡單的解釋:通過Property,我們可以隱藏真實的成員,比如mvarMyProperty我們就可以定義為:
private mvarMyProperty As Object

這樣一來,外界就看不到mvarMyProperty,只能看到MyProperty。當外界對其進行讀寫的時候,中間就有一個處理過程,用來避免對成員的不正確的賦值。其實對於這種情況,java和C++也有類似的做法,就是使用SetMyProperty()函數和GetMyProperty()函數。VB用Property這種特殊的格式將它們做到一起,顯得更簡單方便了。

好了,到這裡,你不想看看完整的例子嗎?這裡重新寫了一個Human類,當中有一個Age(年齡)屬性。我們看看它是怎樣阻止把一個人的年齡設為負值的:
imports System

public module MyModule
sub Main
dim LaoWang as new Human
LaoWang.Name = "老王"
LaoWang.Age = 52
LaoWang.Age = 330 '這句話有沒有把老王的年齡設為330歲呢?看看下一句的結果就知道了。
Console.WriteLine("{0}現在{1}歲。", LaoWang.Name, LaoWang.Age)
Console.ReadLine()
end sub
end module

public class Human
public Name as String
dim mvarAge as integer '這裡沒有指明是public還是private,因為缺省狀態是private

public property Age() as integer
Get
return mvarAge
end Get
Set(Byval Value as integer)
if Value<=0 or Value>=200 then '通常年齡不應該小於1或大於200
Console.WriteLine(Value & "歲?我死了嗎?")
else
mvarAge = value
end if
end set
end property
end class

到這裡你應該閉目養神一會兒:原來屬性是這樣子的啊!








但是話題還沒有完。

比如說,如果成員是一個數組,我該怎樣為它建立屬性呢?為當中的每一個元素建立嗎?那數組大小變化了怎麼辦?Property才不會這麼蠢。我們舉個例子。比方我們給Human類添加一個數組成員Children,表示一個人有多少個孩子。我們先定義mvarChildren:
dim mvarChildren() as Human

為其建立屬性有兩種方式。一種是直接將屬性的類型設為數組:
public property Children() as Human()
Get
return mvarChildren
end Get
Set(Byval Value as Human())
mvarChildren = value
end Set
end property

那麼我們就可以像使用數組一樣來使用這個屬性了。

另一種是在讀取屬性的時候傳入參數index:
Public Property Children(ByVal index As Integer) As Human
Get
Return mvarChildren(index)
End Get
Set(ByVal Value As Human)
mvarChildren(index) = Value
End Set
End Property

這樣可以對傳入的下標進行檢查。
這裡提到讀取屬性的時候可以給參數。這是很有趣的一個東西。比如老王有3個小孩,其中一個叫「王華」。我想根據名字來得到這個小孩,我可以寫一個函數
public function GetChildByName(Byval Name as string) as Human '內容省略了

然後調用
LaoWang.GetChildByName("王華")

就可以了。
要寫成屬性的話,我們可以這樣寫:
public property Child(byval Name as string) as Human
Get
return getChildByName(Name)
end get
set(byval Value as Human)
getChildByName(Name) = Value
end Set
end property

這樣,我們就可以直接使用:
LaoWang.Child("王華").Age = 20

這樣是不是很方便啊?




歡迎光臨 魚骨頭的雲端圖書館 (http://mhfo.hotbbs.info/) Powered by Discuz! 7.0.0