2009-12-24 23 views
10

piton:Python liste sorunu

m=[[0]*3]*2 
for i in range(3): 
    m[0][i]=1 

print m 

Bu kod

[[1, 1, 1], [0, 0, 0]] 

yazdırmak gerektiğini bekliyoruz ama bu tasarım gereğidir

[[1, 1, 1], [1, 1, 1]] 

cevap

14

yazdırır. Bir listenin öğeleri üzerinde çarpma kullandığınızda, referansları yeniden üretiyorsunuz. Değiştirilebilir nesneler için liste başvuruları ile ilgili sorunların ayrıntılarına giren the section "List creation shortcuts" on the Python Programming/Lists wikibook adresine bakın. Eğer ne yaptığınızı anladığınızda

>>> s = [[0]*3 for i in range(2)] 
>>> s 
[[0, 0, 0], [0, 0, 0]] 
>>> s[0][1] = 1 
>>> s 
[[0, 1, 0], [0, 0, 0]] 
6

Bu biraz şeytani, ama oldukça açıktır:

Onların önerilen geçici çözüm bir liste anlama olduğunu. [[0]*3]*2 bitini yaptığınızda, önce 3 sıfır içeren bir liste oluşturuyorsunuz, sonra bunu iki öğe yapmak için kopyalıyorsunuz. Ancak bu kopyayı yaptığınızda, aynı içeriğe sahip yeni listeler oluşturmazsınız, ancak aynı listeye birkaç kez başvurmazsınız. Yani birini değiştirdiğinde, hepsi değişir.

bir örnek vurgulamak için:

In [49]: s = [[]]*2 # Create two empty lists 

In [50]: s # See: 
Out[50]: [[], []] 

In [51]: s[0].append(2) # Alter the first element (or so we think) 

In [52]: s # OH MY, they both changed! (because they're the same list!) 
Out[52]: [[2], [2]]