Globale Variablen der Python-Funktion?

Lesezeit: 8 Minuten

Benutzer-Avatar
Akshat Shekhar

Ich weiß, dass ich aufgrund solcher Verwirrung die Verwendung globaler Variablen von vornherein vermeiden sollte, aber wenn ich sie verwenden würde, ist das Folgende eine gültige Methode, um sie zu verwenden? (Ich versuche, die globale Kopie einer Variablen aufzurufen, die in einer separaten Funktion erstellt wurde.)

x = "somevalue"

def func_A ():
   global x
   # Do things to x
   return x

def func_B():
   x = func_A()
   # Do things
   return x

func_A()
func_B()

Tut das x die die zweite Funktion verwendet, haben denselben Wert wie die globale Kopie von x das func_a verwendet und modifiziert? Spielt die Reihenfolge beim Aufrufen der Funktionen nach der Definition eine Rolle?

  • Achten Sie auch darauf, nicht anzunehmen, nur weil Sie eine Variable in Ihrer Funktion zugewiesen haben, dass Python Referenzen vor der Zuweisung als solche behandelt. Bis zur ersten Zuweisung wäre es bei Verwendung von x weder die globale noch die lokale. Sie werden die berüchtigte UnboundLocalError-Ausnahme in Ihrem Gesicht bekommen 🙂

    – Osirisgothra

    22. August 2015 um 1:42 Uhr

Benutzer-Avatar
Levon

Wenn Sie einfach auf eine globale Variable zugreifen möchten, verwenden Sie einfach ihren Namen. Allerdings zu Rückgeld seinen Wert müssen Sie verwenden global Stichwort.

Z.B

global someVar
someVar = 55

Dies würde den Wert der globalen Variablen auf 55 ändern. Andernfalls würde es nur 55 einer lokalen Variablen zuweisen.

Die Reihenfolge der Auflistungen von Funktionsdefinitionen spielt keine Rolle (vorausgesetzt, sie beziehen sich nicht in irgendeiner Weise aufeinander), die Reihenfolge, in der sie aufgerufen werden, spielt keine Rolle.

  • In dem Code, den ich gegeben habe, macht func_B Dinge (1) mit der globalen Kopie von x (wie von func_A erhalten), (2) mit einer lokalen Variablen x mit dem gleichen Wert wie das Ergebnis von func_A oder (3) mit eine lokale Variable x ohne Wert und (in den Augen des Compilers) ohne Beziehung zu “irgendeinem Wert” oder dem x in func_A?

    – Akshat Shekhar

    14. Mai 2012 um 18:00 Uhr

  • x in func_B ist eine lokale Variable, die ihren Wert aus dem Rückgabewert des Aufrufs von erhält func_A – also denke ich, das würde es zu deinem machen (2)

    – Levon

    14. Mai 2012 um 18:03 Uhr


  • ok, nehmen wir mal an, x wäre eine zufällige Sequenz irgendeiner Art, die von func_A erzeugt wurde (dh dass func_A jedes Mal, wenn es ausgeführt wurde, ein anderes x erzeugte). genannt? Wenn ja, wie kann ich es beheben?

    – Akshat Shekhar

    14. Mai 2012 um 19:00 Uhr

  • Ja, wenn func_A ändert die globale Variable bei jedem Durchlauf und gibt sie an zurück func_B dann zu verwenden func_B wird jedes Mal mit einem geänderten Wert arbeiten. Ich bin mir nicht sicher über Ihr “wie man es repariert”. Vielleicht möchten Sie die hilfreichste Antwort auf Ihre aktuelle/ursprüngliche Frage akzeptieren und dann eine andere Frage stellen, die wie eine Folgefrage aussieht.

    – Levon

    14. Mai 2012 um 19:13 Uhr


  • Eigentlich kommt es darauf an, was x ist. Wenn x unveränderlich ist, bleibt das x in func_B darin, weil es lokal deklariert wird, selbst wenn sie denselben Wert haben. Dies gilt für Tupel, Ints … Wenn es sich beispielsweise um eine Instanz einer Liste handelt und Sie dies tun x.append("...")wird die globale Variable x geändert, da die lokale auf die globale verweist.

    – jadkik94

    14. Mai 2012 um 19:15 Uhr

Benutzer-Avatar
jdotjdot

Innerhalb eines Python-Bereichs erstellt jede Zuweisung an eine Variable, die nicht bereits in diesem Bereich deklariert ist, eine neue lokale Variable wenn nicht Diese Variable wird früher in der Funktion als Verweis auf eine global gültige Variable mit dem Schlüsselwort deklariert global.

Sehen wir uns eine modifizierte Version Ihres Pseudocodes an, um zu sehen, was passiert:

# Here, we're creating a variable 'x', in the __main__ scope.
x = 'None!'

def func_A():
  # The below declaration lets the function know that we
  #  mean the global 'x' when we refer to that variable, not
  #  any local one

  global x
  x = 'A'
  return x

def func_B():
  # Here, we are somewhat mislead.  We're actually involving two different
  #  variables named 'x'.  One is local to func_B, the other is global.

  # By calling func_A(), we do two things: we're reassigning the value
  #  of the GLOBAL x as part of func_A, and then taking that same value
  #  since it's returned by func_A, and assigning it to a LOCAL variable
  #  named 'x'.     
  x = func_A() # look at this as: x_local = func_A()

  # Here, we're assigning the value of 'B' to the LOCAL x.
  x = 'B' # look at this as: x_local="B"

  return x # look at this as: return x_local

Eigentlich könnte man alles umschreiben func_B mit der benannten Variablen x_local und es würde identisch funktionieren.

Die Reihenfolge spielt nur insofern eine Rolle, als Ihre Funktionen Operationen ausführen, die den Wert des globalen x ändern. In unserem Beispiel spielt die Reihenfolge also keine Rolle, da func_B Anrufe func_A. In diesem Beispiel spielt die Reihenfolge eine Rolle:

def a():
  global foo
  foo = 'A'

def b():
  global foo
  foo = 'B'

b()
a()
print foo
# prints 'A' because a() was the last function to modify 'foo'.

Beachten Sie, dass global wird nur benötigt, um globale Objekte zu ändern. Sie können weiterhin innerhalb einer Funktion darauf zugreifen, ohne sie zu deklarieren global. Somit haben wir:

x = 5

def access_only():
  return x
  # This returns whatever the global value of 'x' is

def modify():
  global x
  x = 'modified'
  return x
  # This function makes the global 'x' equal to 'modified', and then returns that value

def create_locally():
  x = 'local!'
  return x
  # This function creates a new local variable named 'x', and sets it as 'local',
  #  and returns that.  The global 'x' is untouched.

Beachten Sie den Unterschied zwischen create_locally und access_onlyaccess_only greift auf das globale x zu, obwohl es nicht aufgerufen wird globalund obwohl create_locally nutzt nicht global entweder erstellt es eine lokale Kopie, da es ist zuordnen ein Wert.

Die Verwirrung hier ist, warum Sie keine globalen Variablen verwenden sollten.

  • Ich denke nicht, dass dies in der Praxis sehr verwirrend ist, Sie müssen nur die Scoping-Regeln von Python verstehen.

    – Casey Kuball

    14. Mai 2012 um 18:21 Uhr

Wie andere angemerkt haben, müssen Sie eine Variable deklarieren global in einer Funktion, wenn Sie möchten, dass diese Funktion die globale Variable ändern kann. Wenn Sie nur darauf zugreifen möchten, brauchen Sie es nicht global.

Um ein bisschen mehr ins Detail zu gehen, was “ändern” bedeutet, ist Folgendes: wenn Sie wollen neu binden den globalen Namen, damit er auf ein anderes Objekt zeigt, muss der Name deklariert werden global in der Funktion.

Viele Operationen, die ein Objekt modifizieren (mutieren). unterlassen Sie Binden Sie den globalen Namen neu, um auf ein anderes Objekt zu verweisen, und so sind sie alles gültig ohne den Namen zu nennen global in der Funktion.

d = {}
l = []
o = type("object", (object,), {})()

def valid():     # these are all valid without declaring any names global!
   d[0] = 1      # changes what's in d, but d still points to the same object
   d[0] += 1     # ditto
   d.clear()     # ditto! d is now empty but it`s still the same object!
   l.append(0)   # l is still the same list but has an additional member
   o.test = 1    # creating new attribute on o, but o is still the same object

Sie können innerhalb einer Funktion direkt auf eine globale Variable zugreifen. Wenn Sie den Wert dieser globalen Variablen ändern möchten, verwenden Sie „global variable_name“. Siehe folgendes Beispiel:

var = 1
def global_var_change():
      global var
      var = "value changed"
global_var_change() #call the function for changes
print var

Im Allgemeinen ist dies keine gute Programmierpraxis. Durch das Brechen der Namespace-Logik kann es schwierig werden, Code zu verstehen und zu debuggen.

Benutzer-Avatar
SoloPilot

Hier ist ein Fall, der mich überrascht hat, als ich einen globalen Wert als Standardwert eines Parameters verwendete.

globVar = None    # initialize value of global variable

def func(param = globVar):   # use globVar as default value for param
    print 'param =', param, 'globVar=", globVar  # display values

def test():
    global globVar
    globVar = 42  # change value of global
    func()

test()
=========
output: param = None, globVar = 42

Ich hatte erwartet, dass param einen Wert von 42 hat. Überraschung. Python 2.7 hat den Wert von globVar ausgewertet, als es zum ersten Mal die Funktion func geparst hat. Das Ändern des Werts von globVar hatte keinen Einfluss auf den param zugewiesenen Standardwert. Das Verzögern der Auswertung, wie im Folgenden, funktionierte wie ich es brauchte.

def func(param = eval("globVar')):       # this seems to work
    print 'param =', param, 'globVar=", globVar  # display values

Oder wenn Sie auf Nummer sicher gehen wollen,

def func(param = None)):
    if param == None:
        param = globVar
    print "param =', param, 'globVar=", globVar  # display values

  • Das erinnerte mich an das Problem von Zuweisen einer leeren Liste als Standardwert. Und, wie im Beispiel, verwenden is zu prüfen, ob etwas ist Noneanstelle des normalen Vergleichs ==.

    – berna1111

    4. März 2020 um 12:48 Uhr

Sie müssen die verwenden global -Deklaration, wenn Sie den einer globalen Variablen zugewiesenen Wert ändern möchten.

Sie brauchen es nicht, um aus einer globalen Variablen zu lesen. Beachten Sie, dass das Aufrufen einer Methode für ein Objekt (auch wenn es die Daten innerhalb dieses Objekts ändert) den Wert der Variablen, die dieses Objekt enthält, nicht ändert (fehlende reflektierende Magie).

  • Das erinnerte mich an das Problem von Zuweisen einer leeren Liste als Standardwert. Und, wie im Beispiel, verwenden is zu prüfen, ob etwas ist Noneanstelle des normalen Vergleichs ==.

    – berna1111

    4. März 2020 um 12:48 Uhr

1090990cookie-checkGlobale Variablen der Python-Funktion?

This website is using cookies to improve the user-friendliness. You agree by using the website further.

Privacy policy