2016-11-22 7 views
0

Es ist eine ziemlich dumme Frage, aber ich bin wirklich verwirrt. Bitte haben einen meinen Code aussehen:Slice verschachtelte Listen

>>> my_list = [1, 2, 3] 
>>> my_list_new = my_list[:] 
>>> my_list_new[0] = 100 
>>> my_list_new 
[100, 2, 3] 
>>> my_list 
[1, 2, 3] 

So funktioniert es wie es sollte. Ich kopierte my_list. Als ich die my_list_new änderte - änderte nur eine Liste.

Jetzt schauen hier:

>>> my_list2 = [[1, 2, 3], [4, 5, 6]] 
>>> my_list_new2 = my_list2[:] 
>>> my_list_new2[0][0] = 100 
>>> my_list_new2 
[[100, 2, 3], [4, 5, 6]] 
>>> my_list2 
[[100, 2, 3], [4, 5, 6]] 

Wie man sehen kann ich geändert my_list_new2, aber beide Listen geändert. Ist es normales Python-Verhalten für verschachtelte Listen? Wie man es vermeidet?

+0

Es gibt zwei gute Antworten unten. Um mehr zu erfahren, klicken Sie hier: https://docs.python.org/2/library/copy.html#module-copy Sie müssen eine 'deepcopy' durchführen, wenn die Liste verschachtelt ist, ansonsten nur die Verweise auf die verschachtelte Liste kopiert. –

+0

Offenbar müssen Sie die Slice-Syntax verwenden, um zu vermeiden, dass nur die Referenz kopiert wird. Ich bin also nicht sicher, warum Sie überrascht sind, dass Listen, die ohne diese Syntax kopiert wurden - nämlich die inneren - nur kopiert wurden durch Bezugnahme. – TigerhawkT3

Antwort

1

Dies sollte in Python

my_list_new2 = [list[:] for list in my_list2] 

Proof

my_list2 = [[1, 2, 3], [4, 5, 6]] 
my_list_new2 = [list[:] for list in my_list2] 
my_list_new2[0][0] = 100 

my_list_new2 
[[100, 2, 3], [4, 5, 6]] 

my_list2 
[[1, 2, 3], [4, 5, 6]] 
1

Liste sind wandelbar beabsichtigt funktionieren. Bedeutung:

a = [1,2,3] 
b = a 
a[0] = 4 
print(b) 

[4, 2, 3]

So im Fall von verschachtelten Listen drucken Wollen Sie die „äußere“ -Liste nur kopieren, und die innere ändern, so dass Sie die andere Liste als auch ändern. Wenn Sie daran interessiert sind nachschlagen Listenzeiger in Python

Lösung:

my_list2 = [[1, 2, 3], [4, 5, 6]] 
my_list_new2 = [inner_lst.copy() for inner_lst in my_list2] # You can use inner_lst[:] as well 
my_list_new2[0][0] = 100 
print(my_list2) 

Returns: [[1, 2, 3], [4, 5, 6]]

-1

Eine Liste von Listen (in Ihrem Fall l1 = [[1, 2, 3], [4, 5, 6]]) enthält Objekte (Liste).

Eine Scheibe einer Liste ist eine neue flache Kopie dieser Teilmenge der Liste, wo es Referenzen auf die Objekte einfügt. Es kann aus dem folgenden Snippet-Code gesehen werden.

l1 = [[1, 2, 3], [4, 5, 6]] 
l2 = l1[:] 

print(id(l1))  # 4406414512 
print(id(l2))  # 4382080248 

# Shallow copy, insert references 
print(id(l1[0])) # 4439177768 
print(id(l2[0])) # 4439177768 

alles zu kopieren, copy.deepcopy verwenden, wo es Kopien der Objekte einfügt. Es kann aus, my_list2 enthält Hinweise auf zwei weitere Listen

import copy 

l1 = [[1, 2, 3], [4, 5, 6]] 
l2 = copy.deepcopy(l1) 

l2[0][0] = 100 

print(l1) # [[1, 2, 3], [4, 5, 6]] 
print(l2) # [[100, 2, 3], [4, 5, 6]] 
-1

Ihre äußere Liste zu sehen.

Auch wenn Sie eine äußere Kopie der äußeren Liste my_list2 erstellen, wird es immer noch (anfangs) die gleichen Elemente enthalten, d. H. Dieselben Verweise auf dieselben zwei Listen. (Wenn Sie mit C/C++ vertraut sind, können Sie sich die Verweise auf Listen als Zeiger vorstellen.) Dies wird als "flache Kopie" bezeichnet. Hier sind ein paar Möglichkeiten, eine flache Kopie zu erstellen:

my_new_list2 = list(my_list2) 
my_new_list2 = [item for item in my_list2] 
my_new_list2 = my_list2[:] 
import copy; my_new_list2 = copy.copy(my_list2) 

Um das Verhalten zu erhalten Sie wollen, müssen Sie die inneren Listen duplizieren.Sie können das von Hand tun, wie andere vorgeschlagen haben - oder Sie können es der Python-Standardbibliothek automatisch erlauben lassen. Das ist, was copy.deepcopy ist für:

import copy 
my_list_new2 = copy.deepcopy(my_list2) 

Der Vorteil deepcopy ist, dass es seinen Weg nach unten einer beliebigen Anzahl von Ebenen der Verschachtelung, die nicht unbedingt nur die ersten inneren Ebene zu arbeiten.

Verwandte Themen