2009-06-05 5 views
15

Mam coś podobnego do tego:C#: Czy podczas dodawania tego samego obiektu do dwóch zmiennych z listy <object> obiekt jest klonowany w procesie?

// Declarations: 
List<SomeType> list1 = new List<SomeType>(); 
List<SomeType> list2 = new List<SomeType>(); 

... 

SomeType something = new SomeType("SomeName"); 
list1.Add(something); 
list2.Add(something); 

... 

list1[indexOfSomething] = new SomeType("SomeOtherName"); 

a obiekt w listy2 nie zmieniło ... Czy to oczekiwanego rezultatu?

Odpowiedz

21

Tak, ale nic nie jest sklonowane. Przed przypisaniem ten sam obiekt znajduje się na obu listach. Po przypisaniu masz dwa unikalne obiekty na dwóch listach.

to zrobić:

list1[indexOfSomething].name = "SomeOtherName"; 

a obiekt w list2 zmieni, też.

+0

Powiedzmy, że SomeType jest interfejsem, a moim celem jest aktualizacja obiektu do innej klasy, która dziedziczy interfejs (nie ten sam kod co powyżej, ponieważ nie można utworzyć interfejsu - mimo to techniczne), byłby jedynym sposobem aby znaleźć obiekt na obu listach i zastąpić je nowym obiektem? Czy jest jakiś inny sprytny sposób? –

+0

"Sprytnym" sposobem byłoby posiadanie jakiegoś typu opakowania, które implementuje interfejs i deleguje do członka, który implementuje ten sam interfejs. Umieść opakowanie na obu listach, a następnie zaktualizuj obiekt, który opakowanie zawiera w jednym miejscu, a obie listy otrzymają aktualizację. –

3

Tak, nie klonujesz obiektu. Obiekt jest dodawany do obu list początkowo przez odniesienie, a następnie przypisywany jest odnośnik na liście do nowego obiektu, który tworzysz.

To zdecydowanie oczekiwany wynik.

4

Nie klonujesz obiektu; dodajesz odnośnik do tego samego obiektu na dwóch listach. Jednak twój kod zastępuje odniesienie na jednej z list odwołaniem do innego obiektu, więc tak, to jest oczekiwane zachowanie.

0

Tak, to jest oczekiwane. Dodano tylko odniesienie do obiektu. Nie sam odnośnik ani kopia.

1

Po przejechaniu „coś” obiekt dodać Cię mijają wartości (C# domyślne), a nie przez odniesienie

+0

Nie sądzę, że to jest poprawne. Przesyłasz referencję według wartości, ale nadal przekazujesz referencję.W przykładzie przypisanie ponownie przypisuje referencję na liście 1, dlatego referencja na liście 2 pozostaje niezmieniona. –

4

Ty zastępując w jednej liście z odniesieniem do nowego obiektu. Jeśli zamiast tego zmienisz właściwość tego obiektu, zobaczysz, że zmieniła się ona w obu miejscach, ponieważ referencja pozostanie taka sama.

6
// Declarations: 
List<SomeType> list1 = new List<SomeType>(); 
List<SomeType> list2 = new List<SomeType>(); 

... 

SomeType something = new SomeType("SomeName"); 
list1.Add(something); 
list2.Add(something); 

Pamiętaj, że po dodaniu obiektu do listy, po prostu dodajesz wskaźnik do obiektu. W tym przypadku lista1 i lista2 wskazują na ten sam adres w pamięci.

list1[indexOfSomething] = new SomeType("SomeOtherName"); 

Teraz przypisałeś element list1 do innego wskaźnika.

Naprawdę nie klonujesz obiektów, kopiujesz wskaźniki, które akurat wskazują na ten sam obiekt. Jeśli potrzebujesz dowodu, wykonaj następujące czynności:

SomeType something = new SomeType("SomeName"); 
list1.Add(something); 
list2.Add(something); 

list1[someIndex].SomeProperty = "Kitty"; 

bool areEqual = list1[someIndex].SomeProperty == list2[someIndex].SomeProperty; 

areEqual powinno być prawdą. Wskaźniki rocka!