Seite 1 von 1

Namensraum und Default-Parameter

Verfasst: Montag 11. September 2006, 20:13
von hgr00
Hallo zusammen,

ich habe ein Frage zum Python-Namensraum (und hoffe, dass ich keinen Thread dazu übersehen habe - wäre ein schlechter Einstieg ins Forum). Folgendes kleines Programm:

Code: Alles auswählen

def foo(a = {}):
  print a
  a.update({1: 2})

foo()
foo()
bringt die folgende Ausgabe:

Code: Alles auswählen

{}
{1: 2}
Warum? Die Funktion hat den Parameter a, der defaultmäßig leer ist und sie wird zwei Mal ohne Parameter aufgerufen. Warum bekomme ich dann beim zweiten Aufruf kein leeres Dictionary ausgegeben?


Viele Grüße

hgr00

Verfasst: Montag 11. September 2006, 21:02
von Monk
Standardfehler: Der Vorgabewert wird nur einmal ausgewertet, nämlich beim ersten Aufruf.

So gehts richtig:

Code: Alles auswählen

def foo(a = None):
  if a == None:
    a = {}
  print a
  a.update({1:2})
Statt None kannst Du auch einen beliebigen konstanten Wert nehmen, aber eben nie ein veränderbares Objekt. Da ein Dictionary ein solches veränderbares Objekt ist, wird es genau einmal erzeugt und dann bei jedem Aufruf mit Standardparameter verwendet.

Gruß, der Monk

Verfasst: Dienstag 12. September 2006, 06:47
von BlackJack
Monk hat geschrieben:Standardfehler: Der Vorgabewert wird nur einmal ausgewertet, nämlich beim ersten Aufruf.
Nicht beim ersten Aufruf, sondern wenn das ``def`` ausgeführt wird.

Verfasst: Dienstag 12. September 2006, 12:07
von Monk
BlackJack hat geschrieben:Nicht beim ersten Aufruf, sondern wenn das ``def`` ausgeführt wird.
Mist, da war noch was... aber mal eine Gegenfrage: Wie ist das bei vorkomplierten Dateien (.pyc). Wird das def mit der Auswertung der Default-Parameter da bereits bei der Kompilierung oder erst beim Start ausgeführt?

Gruß, der Monk

Verfasst: Mittwoch 13. September 2006, 12:41
von BlackJack
Erst beim Start, also wieder wenn ``def`` ausgeführt wird. Das wäre sonst auch etwas inkonsistent, wenn sich der pyc-Code anders verhalten würde als der Quelltext aus dem der Bytecode generiert wurde. Zum Beispiel:

Code: Alles auswählen

import sys
def test(arg=sys.platform)
Da würde es plötzlich einen Unterschied machen wenn die *.pyc Datei unter Linux erstellt wurde, aber dann unter MacOS ausgeführt wird.

Verfasst: Donnerstag 14. September 2006, 20:56
von Joghurt
Monk hat geschrieben:Mist, da war noch was... aber mal eine Gegenfrage: Wie ist das bei vorkomplierten Dateien (.pyc).
Python macht folgendes:
  1. Wenn .pyc Datei vorhanden und aktueller als .py Datei, lade Bytecode und gehe zu Schritt 4
  2. Compiliere .py in bytecode
  3. Wenn das Verzeichnis beschreibbar ist, speichere Bytecode in die .pyc Datei
  4. Führe Bytecode aus
Also kann es keinen Unterschied machen.