2015-04-02 21 views
0

如何從列表中獲取作爲新副本/實例的項目,以便稍後使用和更改它,而不更改原始對象列表?從列表中獲取作爲新副本的項目(不作爲原始參考)

Public Class entry 
    Public val As String 
    ' ... other fields ... 
End Class 

Dim MyList As New List(Of entry) 
Dim newitem As New entry 
newitem.val = "first" 
MyList.Add(newitem) 

現在,如果我嘗試從這個名單得到一個項目,將其更改爲別的東西,它改變在列表中的原始項目,以及(它被用作不是一個新實例的引用)。

Dim newitem2 As New entry 
newitem2 = MyList.Item(0) 
newitem2.val = "something else" 

所以現在MyList.item(0).val包含「別的東西」,但我只希望newitem2包含給定域的新值,並從該列表中的對象保留其他值。

有沒有辦法做到這一點,而不是一個一個地重新分配所有的領域?

回答

2

如果entry被定義爲引用類型(Class),那麼您唯一的選擇是顯式創建一個與原始值具有相同值的新實例。例如:

Public Partial Class Entry 
    Public Function Clone() As Entry 
     Return New Entry() With { .val = Me.val, … } 
    End Function 
End Class 

(.NET框架類庫從早期定義的類型ICloneable正是這種目的的類型沒有真正流行就因爲某些原因。)

要知道,你可能有要遞歸地做到這一點,也就是說,如果你的類包含了引用類型的字段,你也必須克隆存儲在這些字段中的對象。

然後,而不是做這樣的:

Dim newitem2 As New entry ' (Btw.: `New` is superfluous here, since you are 
newitem2 = MyList.Item(0) '   going to throw away the created instance here.) 

這樣做:

Dim newitem2 As Entry = MyList.Item(0).Clone() 

一種替代方法是使用值類型(即宣告你的項目類型爲Structure)。值類型在傳遞時自動被複制。不過,也有很多需要注意的地方觀察,其中:

  • 不這樣做,如果你的類型包含許多領域。 (爲什麼?許多字段通常意味着類型將在內存中佔用更多字節,如果對象變得太大,則頻繁複制會相當昂貴)。

  • 值類型應該是不可變類型。 (爲什麼?參見例如Why are mutable structs evil?

這些只是兩個指導原則。你可以找到更多infornation關於這個話題在這裏:

+0

謝謝你的答案廣泛。很多有用的信息。現在我正在考慮使用'IClonable'這樣的東西,但是我也會讀'Struct'。 – 2015-04-02 07:54:09

相關問題