Seite 2 von 2
Verfasst: Dienstag 19. Juni 2007, 07:52
von Michael Schneider
rolgal_reloaded hat geschrieben:
Alles klar, aber wäre es nicht doch besser, die Defaultwerte in __init__ reinzuschreiben. Entspricht das nicht mehr der Idee eines Konstruktors?
Also:
Code: Alles auswählen
class A:
def __init__(self, var1 = [], var2 = []): #usw.
self.var1 = var1
self.var2 = var2
Es gibt eine Initialisierung der Klasse (i.d.R. beim Programmstart ausgeführt) und je eine Initialisierung pro Instanz. Was Du jetzt geschrieben hast, entspricht
[EDIT: ebenfalls nicht (siehe BlackJacks Erklärung unten)] grandmas Vorschlag. Allein der Zweck entscheidet hier, wo man Namen initialisiert. Aber ich finde, Du hast Recht: Konstanten kann man im Namensraum der Klasse definieren.
Grüße,
Michael
Verfasst: Dienstag 19. Juni 2007, 08:20
von rolgal_reloaded
Danke für die Klarstellung, wieder was wichtiges konkretisiert im Oberstübchen,
liebe Grüße
rolgal_reloaded
Verfasst: Dienstag 19. Juni 2007, 09:37
von BlackJack
rolgal_reloaded hat geschrieben:Alles klar, aber wäre es nicht doch besser, die Defaultwerte in __init__ reinzuschreiben. Entspricht das nicht mehr der Idee eines Konstruktors?
Also:
Code: Alles auswählen
class A:
def __init__(self, var1 = [], var2 = []): #usw.
self.var1 = var1
self.var2 = var2
Oder gibt es Fälle wo das wie vom Autor des Threads gezeigt wird besser ist?
Das ist nicht viel anders oder besser als Klassenattribute weil die Defaultwerte, genau wie Klassenattribute nur *einmal* ausgewertet werden, nämlich wenn das ``def __init__(...)`` ausgeführt wird:
Code: Alles auswählen
In [1]: class A(object):
...: def __init__(self, var1=[], var2=[]):
...: self.var1 = var1
...: self.var2 = var2
...:
In [2]: x = A()
In [3]: y = A()
In [4]: x.var1.append(42)
In [5]: x.var1
Out[5]: [42]
In [6]: y.var1
Out[6]: [42]
In [7]: x.var1 is y.var1
Out[7]: True
Auch das ist sehr wahrscheinlich nicht das Verhalten was man im allgemeinen Fall gerne hätte.
Verfasst: Dienstag 19. Juni 2007, 10:55
von rolgal_reloaded
@BlackJack
Hast es wieder geschafft mich zu verwirren bzw. mir klar zu machen, dass mir da etwas ganz und gar nicht so klar ist.
Dass sich die Modifizierung von Klassenattributen auf alle Instanzen auswirken kann, wie von Michael gezeigt, erscheint mir logisch.
Aber warum denn in meinem Beispiel. Und warum passiert hier was anderes:
Code: Alles auswählen
>>> class A(object):
def __init__(self):
self.var1 = []
self.var2 = []
>>> x = A()
>>> y = A()
>>> x.var1.append(42)
>>> x.var1
[42]
>>> y.var1
[]
>>>
LG
rolgal_reloaded
Verfasst: Dienstag 19. Juni 2007, 11:24
von grandma
Das wird ja noch richtig interessant hier.
Ich habe auch keine Ahnung warum sich hier in den anderen Objekten etwas ändert.
Ich hab mal den Threadtitel umbenannt...
Verfasst: Dienstag 19. Juni 2007, 12:22
von BlackJack
Die Erklärung habe ich eigentlich schon gegeben:
Code: Alles auswählen
class A(object):
def __init__(self, var1=[]):
self.var1 = var1
self.var2 = []
Der Ausdruck hinter dem '=' in der Funktionsdefinition wird ein einziges mal ausgewertet, nämlich dann wenn das ``def`` als Teil der Klassendefinition ausgeführt wird. Das Ergebnis dieses Ausdrucks wird bei jedem Aufruf der Methode an den Namen `var1` gebunden. Das ist immer die selbe Liste.
Der Körper der Funktion wird dagegen bei jedem Aufruf der Funktion abgearbeitet. Das heisst `self.var2` wird jedesmal an eine neue Liste gebunden.
Verfasst: Dienstag 19. Juni 2007, 17:10
von rolgal_reloaded
BlackJack hat geschrieben:Die Erklärung habe ich eigentlich schon gegeben:
Naja, so wie oben eben nicht, sonst hätte ich (wir) nicht nachgefragt
Jetzt ist klar warum das so ist.
Aber ist das eigentlich gut, dass es so ist, oder sollte das nicht anders sein??
Oder anders gesagt: weiss ich jetzt endlich, warum ein Konstruktor wie am Anfang des Threads gezeigt sinnvoll sein kann.
LG
rolgal_reloaded
Verfasst: Mittwoch 20. Juni 2007, 15:36
von rolgal_reloaded
Also ich finde das immer noch schräg......
Wer noch, oder wer nicht? Und vor allem wenn nicht, W A R U M ???
Verfasst: Mittwoch 20. Juni 2007, 18:19
von BlackJack
An der Stelle muss(te) man ein Entscheidung treffen: Werden Default-Werte einmal berechnet wenn die Funktion definiert wird, oder jedesmal wenn die Funktion aufgerufen wird.
Zwei Gründe für's einmalige berechnen:
a) Es muss nur einmal gemacht werden.
b) Berechnen bei jedem Funktionsaufruf kann man auch *in* der Funktion machen, wenn man das braucht.
In den allermeisten Fällen sind die Default-Werte in der Praxis nach meiner Erfahrung sowieso "immutables", da braucht man nur eine Auswertung.
Verfasst: Mittwoch 20. Juni 2007, 18:43
von rolgal_reloaded
@BlackJack
...was meinst du jetzt mit immutables? - Beispiel?
LG
rolgal_reloaded
Verfasst: Mittwoch 20. Juni 2007, 18:55
von Zap
Blick zwar schon lange nicht mehr was hier so diskutiert wird
aber immutables kenne ich
Code: Alles auswählen
# Immutables ( unveränderbar )
# Unter anderem keine in-place modifikation möglich
"..." # Strings
1 # int
1.2 # float
# Mutables ( veränderbare )
[] # lists
{} # dicts
So mal als Beispiel

Verfasst: Mittwoch 20. Juni 2007, 18:57
von rolgal_reloaded
Zap hat geschrieben:Blick zwar schon lange nicht mehr was hier so diskutiert wird
aber immutables kenne ich
Code: Alles auswählen
# Immutables ( unveränderbar )
# Unter anderem keine in-place modifikation möglich
"..." # Strings
1 # int
1.2 # float
# Mutables ( veränderbare )
[] # lists
{} # dicts
So mal als Beispiel

Ach so,.....alles klar!
Danke!
Verfasst: Mittwoch 20. Juni 2007, 19:01
von Michael Schneider
rolgal_reloaded hat geschrieben:@BlackJack
...was meinst du jetzt mit immutables? - Beispiel?
Hi,
auch wenn ich nicht gefragt wurde:
Unveränderliche Objekte in Python sind Strings, Integer, Long, Float, Tupel
Veränderliche Objekte sind Listen und Dictionaries.
Beispiele findest Du weiter oben im Thread.
Grüße,
der Michel
Verfasst: Mittwoch 20. Juni 2007, 19:04
von Michael Schneider
Man, das geht aber auch schnell hier... erst gestern immer auf das vorletzte Posting antwortet, heute schieben sich schon zwei dazwischen.
Michael
Verfasst: Mittwoch 20. Juni 2007, 19:08
von rolgal_reloaded
[/quote]
Unveränderliche Objekte in Python sind Strings, Integer, Long, Float, Tupel
Veränderliche Objekte sind Listen und Dictionaries.
Beispiele findest Du weiter oben im Thread.
Grüße,
der Michel[/quote]
Mann, ich Hirsch, weiss ich doch, aber immutables, also der englische Terminus war mir grad nicht geläufig-----

in Zukunft 5 Minuten nachdenken, bevor ich überflüssige Fragen stelle
