物件初始化表達式可讓您使用單一表達式來指定複雜對象的屬性。 它們可用來建立具名型別和匿名型別的實例。
聲明
具名和匿名型別實例的宣告看起來幾乎完全相同,但其效果並不相同。 每個類別都有自己的功能和限制。 下列範例示範使用物件初始化表達式清單來宣告及初始化具名類別 Customer實例的便利方式。 請注意,類別的名稱是在 關鍵詞 New之後指定。
Dim namedCust = New Customer With {.Name = "Terry Adams"}
匿名類型沒有可用名稱。 因此,匿名類型的具現化不能包含類別名稱。
Dim anonymousCust = New With {.Name = "Hugo Garcia"}
兩個宣告的需求和結果不同。 針對 namedCust, Customer 具有 屬性的 Name 類別必須已經存在,而且宣告會建立該類別的實例。 針對 anonymousCust,編譯程式會定義具有一個屬性的新類別、名為 Name的字串,並建立該類別的新實例。
具名類型
物件初始化表達式提供簡單的方法來呼叫型別的建構函式,然後在單一語句中設定部分或所有屬性的值。 編譯程式會為語句叫用適當的建構函式:如果未顯示任何自變數,則為無參數建構函式,如果傳送一或多個自變數,則為參數化建構函式。 之後,指定的屬性會以初始化表達式清單中呈現的順序初始化。
初始化表達式清單中的每個初始化都包含將初始值指派給 類別的成員。 定義 類別時,會決定成員的名稱和數據類型。 在下列範例中,類別Customer必須存在,而且必須具有具名NameCity且可接受字串值的成員。
Dim cust0 As Customer = New Customer With {.Name = "Toni Poe",
.City = "Louisville"}
或者,您可以使用下列程式代碼來取得相同的結果:
Dim cust1 As New Customer With {.Name = "Toni Poe",
.City = "Louisville"}
每個宣告都相當於下列範例,它會使用無參數的建構函式建立Customer物件,然後使用Name語句來指定City和With屬性的初始值。
Dim cust2 As New Customer()
With cust2
.Name = "Toni Poe"
.City = "Louisville"
End With
如果類別 Customer 包含具參數的建構函式,允許您傳遞一個值給 Name,例如,您也可以以下列方式宣告和初始化 Customer 物件:
Dim cust3 As Customer =
New Customer("Toni Poe") With {.City = "Louisville"}
' --or--
Dim cust4 As New Customer("Toni Poe") With {.City = "Louisville"}
您不需要初始化所有屬性,如下列程式代碼所示。
Dim cust5 As Customer = New Customer With {.Name = "Toni Poe"}
不過,初始化清單不能是空的。 未初始化的屬性會保留其預設值。
具名型別的類型推斷
通過結合物件初始化運算式和局部類型推斷,您可以縮短 cust1 的宣告程式代碼。 這可讓您省略 As 變數宣告中的 子句。 變數的數據類型是從指派所建立的物件類型推斷而來。 在下列範例中,的 cust6 型別為 Customer。
Dim cust6 = New Customer With {.Name = "Toni Poe",
.City = "Louisville"}
具名類型的備註
類別成員無法在物件初始化表達式清單中初始化一次以上。 的
cust7宣告會造成錯誤。'' This code does not compile because Name is initialized twice. ' Dim cust7 = New Customer With {.Name = "Toni Poe", ' .City = "Louisville", ' .Name = "Blue Yonder Airlines"}成員可用來初始化本身或其他欄位。 如果成員在初始化之前存取,如以下
cust8宣告所示,將會使用預設值。 請記住,處理使用物件初始化表達式的宣告時,第一件事就是叫用適當的建構函式。 之後,初始化表達式清單中的個別欄位會初始化。 在下列範例中,會為Name指派預設值到cust8,並在cust9中指派已初始化的值。Dim cust8 = New Customer With {.Name = .Name & ", President"} Dim cust9 = New Customer With {.Name = "Toni Poe", .Title = .Name & ", President"}下列範例使用 和
cust3cust4參數化建構函式來宣告和初始化cust10和cust11。Dim cust10 = New Customer("Toni Poe") With {.Name = .Name & ", President"} ' --or-- Dim cust11 As New Customer("Toni Poe") With {.Name = .Name & ", President"}物件初始化表達式可以是巢狀的。 在下列範例中,
AddressClass是一個具有兩個屬性City和State的類別,而類別Customer具有一個名為Address的屬性,該屬性是AddressClass的實例。Dim cust12 = New Customer With {.Name = "Toni Poe", .Address = New AddressClass With {.City = "Louisville", .State = "Kentucky"}} Console.WriteLine(cust12.Address.State)初始化清單不能是空的。
正在初始化的實例不能是 Object 類型。
初始化的類別成員不能是共享成員、只讀成員、常數或方法呼叫。
被初始化的類別成員無法編製索引或限定。 下列範例會引發編譯程序錯誤:
'' Not valid.' Dim c1 = New Customer With {.OrderNumbers(0) = 148662}' Dim c2 = New Customer with {.Address.City = "Springfield"}
匿名類型
匿名型別使用物件初始化器來建立您未明確定義和命名的新型別物件。 相反地,編譯程式會根據您在物件初始化表達式清單中指定的屬性產生類型。 因為未指定型別的名稱,所以稱為 匿名型別。 例如,將下列宣告與 先前的 宣告 cust6進行比較。
Dim cust13 = New With {.Name = "Toni Poe",
.City = "Louisville"}
唯一的差異語法是數據類型之後 New 未指定任何名稱。 然而,發生的情況大不相同。 編譯程式會定義具有兩個屬性的新匿名型別, NameCity並使用指定的值建立它的實例。 型別推斷會決定範例中Name和City的型別為字串。
謹慎
匿名型別的名稱是由編譯程式所產生,而且可能會因編譯而異。 您的程式代碼不應該使用或依賴匿名類型的名稱。
因為類型的名稱無法使用,所以您無法使用 As 子句來宣告 cust13。 必須推斷其類型。 如果沒有使用晚期系結,這會將匿名型別的使用限制為局部變數。
匿名類型提供LINQ查詢的重要支援。 如需在查詢中使用匿名型別的詳細資訊,請參閱Visual Basic中的 匿名型 別和 LINQ簡介。
匿名類型的備註
一般而言,匿名型別宣告中所有或大部分的屬性都是索引鍵屬性,以在屬性名稱前面輸入 關鍵詞
Key來表示。Dim anonymousCust1 = New With {Key .Name = "Hugo Garcia", Key .City = "Louisville"}如需金鑰屬性的詳細資訊,請參閱 金鑰。
如同具名型別,匿名型別定義的初始化表達式清單必須宣告至少一個屬性。
Dim anonymousCust = New With {.Name = "Hugo Garcia"}宣告匿名型別的實例時,編譯程式會產生相符的匿名型別定義。 屬性的名稱和數據類型取自實例宣告,並由編譯程式包含在定義中。 屬性不會像具名類型那樣事先命名和定義。 這些類型已被推斷出來。 您無法使用
As子句來指定屬性的數據類型。匿名型別也可以透過其他幾種方式建立其屬性的名稱和值。 例如,匿名型別屬性可以同時取得變數的名稱和值,或是另一個物件之屬性的名稱和值。
' Create a variable, Name, and give it an initial value. Dim Name = "Hugo Garcia" ' Variable anonymousCust2 will have one property, Name, with ' "Hugo Garcia" as its initial value. Dim anonymousCust2 = New With {Key Name} ' The next declaration uses a property from namedCust, defined ' in an earlier example. After the declaration, anonymousCust3 will ' have one property, Name, with "Terry Adams" as its value. Dim anonymousCust3 = New With {Key namedCust.Name}如需在匿名類型中定義屬性之選項的詳細資訊,請參閱 如何:推斷匿名類型宣告中的屬性名稱和類型。