Mag mir jemand dieses Verhalten erklären?

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
bremer
User
Beiträge: 109
Registriert: Sonntag 25. Mai 2008, 00:13

Freitag 26. Dezember 2008, 20:48

Code: Alles auswählen

>>> x = y = 5
>>> x, y
(5, 5)
>>> y = 10
>>> x, y
(5, 10)
>>> x = y = [1, 2, 3]
>>> x, y
([1, 2, 3], [1, 2, 3])
>>> y.append(4)
>>> x, y
([1, 2, 3, 4], [1, 2, 3, 4])
>>> x.append(5)
>>> x, y
([1, 2, 3, 4, 5], [1, 2, 3, 4, 5])
Wie kommt es, dass die Methode an die jeweils andere Variable ebenfalls weitergereicht wird, während eine Neuzuweisung nur auf eine wirkt?

Was passiert dort im Hintergrund?
Darii
User
Beiträge: 1177
Registriert: Donnerstag 29. November 2007, 17:02

Freitag 26. Dezember 2008, 20:54

Weil x und y auf dieselbe Liste zeigen.

Code: Alles auswählen

>>> x = y = [1, 2, 3]
>>> x is y
True
Benutzeravatar
sehbaer
User
Beiträge: 39
Registriert: Sonntag 30. März 2008, 17:26
Wohnort: Kölle

Freitag 26. Dezember 2008, 20:56

im ersten Fall bindest Du y an ein neues Objekt: 10. Im Zweiten Fall änderst Du das Objekt an das y (und x) gebunden ist.

Wenn Du im erstel Fall das Objekt 5 auf 10 ändern könntest, würdest Du auch hier das gleiche Verhalten wie in Fall zwei beobachten können.
...es sind ganz bestimmt mehr Nullen als Einsen.
Benutzeravatar
Trundle
User
Beiträge: 591
Registriert: Dienstag 3. Juli 2007, 16:45

Freitag 26. Dezember 2008, 20:57

Bei Python werden Objekte an Namen gebunden.
Mit

Code: Alles auswählen

x = y = [1,2,3]
hast du die selbe Liste jetzt an zwei verschiedene Namen gebunden und die `append`-Methode verändert das Objekt, also die Liste.

Wenn du jetzt aber

Code: Alles auswählen

x = list()
schreibst, dann zeigt `x` auf ein anderes Objekt (in dem Fall eine neue, leere Liste) als `y`.
"Der Dumme erwartet viel. Der Denkende sagt wenig." ("Herr Keuner" -- Bertolt Brecht)
Benutzeravatar
pysq
User
Beiträge: 31
Registriert: Samstag 29. November 2008, 17:48

Freitag 26. Dezember 2008, 22:16

wenn du 2 identische listen haben willst, die nicht das gleiche Objekt referenzieren:

Code: Alles auswählen

x=[1, 2, 3]
y=x[:]
mfg pysq
DasIch
User
Beiträge: 2465
Registriert: Montag 19. Mai 2008, 04:21
Wohnort: Berlin

Freitag 26. Dezember 2008, 22:56

bremer hat geschrieben:Wie kommt es, dass die Methode an die jeweils andere Variable ebenfalls weitergereicht wird, während eine Neuzuweisung nur auf eine wirkt?
In dem Satz ist ein grundlegender Fehler vorhanden der dein Verständnis beeinflusst: Die Bezeichnung Variable. Im Gegensatz zu Sprachen wie z.B. C gibt es in Python keine Variablen.

Es gibt Objekte und Referenzen auf diese.

Code: Alles auswählen

foo = 1
1 ist hier ein Objekt und foo ist ein Name, dieser Name stellt die Referenz zu dem Objekt 1 dar. Schreibe ich:

Code: Alles auswählen

foo = bar = 1
Habe ich wieder ein Objekt 1 und diesmal zwei Namen die Referenzen auf 1 sind.

Wenn ich nun foo ein neues Objekt zuweise, z.B. so:

Code: Alles auswählen

foo = 2
Ist foo eine Referenz auf dass Objekt 2. bar zeigt weiterhin auf dass immernoch existierende Objekt 1.

An dieser Stelle ist vielleicht ein Blick auf "del" interessant, del löscht Referenzen auf Objekte aber nicht das Objekt. Objekte werden vom GC entfernt wenn es keine Referenz mehr gibt (in der Praxis variert das je nach Implementation leicht, CPython cacht z.B. Integer dass führt zu verwirrenden Effekten bei dem Operator is).

Kommen wir zu einer Liste, einem veränderbaren Objekt.

Du hast in deinem Beispiel 2 Namen, die jeweils eine Referenz auf ein und dieselbe Liste sind. Du veränderst diese Liste mit der Methode append und völlig egal welche Referenz du dafür verwendet hast beide Referenzen zeigen immer noch auf die Liste, welche du verändert hast.

Ich hoffe dass war verständlich ansonsten ist vielleicht noch dieser, imho ziemlich gelungene, Blog Artikel von dennda interessant.
Benutzeravatar
str1442
User
Beiträge: 520
Registriert: Samstag 31. Mai 2008, 21:13

Samstag 27. Dezember 2008, 08:45

Siehe auch diesen Thread http://www.python-forum.de/topic-16761.html
Grade mein "Bücherbeispiel" empfinde ich als sehr anschaulich ^_^
Antworten