2016-06-30 6 views
-1

Say Ich habe eine Funktion foo, die eine Liste baz nimmt, und in foo wollte ich baz klar wie so:Python Pointer Mehrdeutigkeit

baz = [] 
foo(baz) 

foo(baz): 
    baz = [] 

Nun ist dieser Code nicht tun, was ich würde es tun möchte, , weil es eine neue lokale Liste namens baz erstellt. Ich weiß, dass es andere Möglichkeiten gibt, dies zu tun, aber ich möchte Python wissen Zweideutigkeiten wie diese löst, wo die Anweisung

baz = [] 

als zu sagen Python interpretiert werden, um die äußere Umfang baz Variable auf einen neuen leeren Brocken Punkt oder um einen neuen Zeiger zu erstellen, der auf einen leeren Speicherbereich zeigt.

EDIT

Bitte beachten Sie, dass ich nicht zu fragen, wie eine Liste zu löschen. Ich frage nach dem Verhalten des Python-Interpreters. Bitte lesen Sie die Frage klar vor dem Abstimmen.

+1

Nun, ich weiß, wie die Liste zu löschen. Ich habe gerade del foo [:] Ich habe mich gefragt, wie der Python-Dolmetscher eine solche Situation sieht. –

+0

Die Zuweisung wird immer als lokale Variable interpretiert, es sei denn, Sie verwenden das Schlüsselwort 'global'. Sie haben jedoch den Parameter 'baz' benannt, so dass Sie nicht auf den globalen' baz' verweisen dürfen. Python-Variablen sind nicht wie C-, Java-Variablen. Sehen Sie sich dieses großartige Gespräch an: https://www.youtube.com/watch?v=_AEJHKGk9ns –

+0

Sie können das Verhalten des Interpreters sehen, indem Sie Code ausführen. Worum fragst du eigentlich? Variabler Umfang? – TigerhawkT3

Antwort

2

Python behandelt die Zuweisung von Variablen nur dann als Zuordnung zu einer Variablen aus einem äußeren Bereich, wenn Sie dies explizit mit den Schlüsselwörtern global oder nonlocal angeben.global ist für globale Variablen und nonlocal ist ein Python-3-exklusives Schlüsselwort für die Schließung Variablen:

x = 1 
def change_x(): 
    global x 
    x = 2 
def dont_change_x(): 
    # no global 
    x = 3 

change_x() 
print(x) # prints 2 

dont_change_x() 
print(x) # still prints 2 

Ansonsten wird es immer Aufgabe interpretiert als ein lokale Variablen zuweisen.

1

Wenn Sie die Elemente in der Liste zu löschen beabsichtigen, würden Sie nicht den aktuellen Namen zu einer neuen Liste zuweisen müssen, löschen Sie einfach die alte von Aufschneiden:

foo(baz): 
    baz[:] = [] # clears out list baz 

baz[:] ist ein Weg, der Indizierung alle Elemente in Ihrer Liste und ihnen einen neuen Wert

aktualisieren Zuordnung:

Wenn Sie das gleiche in einer Zuweisung t verwenden oa neue Liste, ordnet der Dolmetscher einfach diesen Namen auf ein neues list Objekt:

>>> baz = [] 
>>> id(baz) 
14832064 
>>> baz = [] 
>>> id(baz) 
14834304 

Außer Sie verwenden Schneiden die alte Liste Refactoring, der Name baz wird nicht mehr ein Verweis auf die old Liste .

+0

Das fragt der Fragesteller nicht. – user2357112

0

Verwendung Slicing:

>>> def foo(baz): 
...  baz[:] = [] 
... 
>>> baz = [1, 2] 
>>> foo(baz) 
>>> baz 
[] 

Die my_list[:] Python sagt alle Elemente in my_list mit dem Inhalt auf der rechten Seite der Zuweisungsanweisung zu ersetzen, die dich auf das gleiche my_list Objekt.

+0

Das fragt der Fragesteller nicht. – user2357112

+0

@ user2357112 - Ich denke es ist, so ist die Frage offenbar weniger klar als ich dachte. Ich werde auf eine Klarstellung warten. – TigerhawkT3

+0

Der Fragesteller hat nun eine Klärung in einem Kommentar zu der Frage gegeben. – user2357112

-1

Wenn Sie die Liste löschen möchten, verwenden Sie .clear() stattdessen eine neue Liste zu erstellen:

def foo(baz): 
    baz.clear() 

Side Hinweis: Um die äußere baz in Ihrem foo() zugreifen können Sie global Schlüsselwort verwenden. In diesem Fall gibt es jedoch keine Mehrdeutigkeiten, da Python Sie zwingt, das Argument umzubenennen, indem Sie SyntaxError werfen.

def foo(baz2): 
    global baz 
    baz = [] 

Plase zur Kenntnis, dass die Nutzung von global abgeraten.

+0

Das ist nicht notwendig; OP gibt bereits einen Verweis auf die Liste als Argument weiter. – TigerhawkT3

+2

Darüber hinaus kann Baz nicht global und ein Parameter sein. –

+1

Verwenden Sie keine Globals, außer andere Optionen sind schlechter. Sie sind in diesem Fall nicht – GingerPlusPlus

1

Werfen Sie einen Blick auf diesen Beitrag, um Python Weg von passing parameters by assignment zu verstehen.

Was passiert ist, dass Sie die Variable Baz zu einer anderen Liste neu definieren, so dass es nicht mehr den Verweis auf den äußeren Baz hat. Sie müssen die Elemente in der Liste direkt bearbeiten.

Zum Beispiel, wenn Sie ein Element sind das Hinzufügen Baz wird die äußere Liste der Änderungen erhalten:

def foo(baz): 
    baz.append('baz') 

Aber dies zu tun:

def foo(baz): 
    baz = [] 

Sie ordnen eine neue Liste Baz und der Hinweis auf deinen äußeren Baz ist jetzt gebrochen.

In Ihrem Fall haben Sie zwei Möglichkeiten, die Liste zu löschen:

del baz[:] 
baz[:] = []