Python. Merkwürdige Klassenattribute Verhalten

>>> class Abcd: ... a = '' ... menu = ['a', 'b', 'c'] ... >>> a = Abcd() >>> b = Abcd() >>> aa = 'a' >>> ba = 'b' >>> aa 'a' >>> ba 'b' 

Es ist alles richtig und jedes Objekt hat eigene 'a', aber …

 >>> a.menu.pop() 'c' >>> a.menu ['a', 'b'] >>> b.menu ['a', 'b'] 

Wie konnte das passieren? Und wie man die Liste als Klassenattribut verwendet?

3 Solutions collect form web for “Python. Merkwürdige Klassenattribute Verhalten”

Dies ist, weil die Art und Weise Sie Initialisierung der menu Eigenschaft ist die Einstellung aller Instanzen auf die gleiche Liste, im Gegensatz zu verschiedenen Listen mit dem gleichen Wert.

Verwenden __init__ stattdessen die __init__ der Klasse, um Werte zu initialisieren, wodurch eine neue Liste erstellt und diese Liste der Eigenschaft für die jeweilige Instanz der Klasse __init__ :

 class Abcd: def __init__(self): self.a = '' self.menu = ['a', 'b', 'c'] 

Siehe Klassenobjekte im Tutorial und bemerke die Verwendung von self .

Verwenden Sie Instanzattribute, keine Klassenattribute (und auch neue Stilklassen):

 >>> class Abcd(object): ... def __init__(self): ... self.a = '' ... self.menu = ['a','b','c'] ... >>> a=Abcd() >>> b=Abcd() >>> aa='a' >>> ba='b' >>> aa 'a' >>> ba 'b' >>> a.menu.pop() 'c' >>> a.menu ['a', 'b'] >>> b.menu ['a', 'b', 'c'] >>> 

Denn Variablen in Python sind nur "Etiketten"

Sowohl Abcd.menu als auch a.menu verweisen auf das gleiche Listenobjekt.

In diesem Fall solltest du das Label einem neuen Objekt zuordnen,

Das Objekt nicht anstelle

Du kannst rennen

 a.menu = a.menu[:-1] 

Anstatt von

 a.menu.pop() 

Den Unterschied fühlen

Python ist die beste Programmiersprache der Welt.