Frage von DepravedGirl, 60

Wie kann man Variablen in der Programmiersprache Python 3.4 innerhalb einer Funktion lokal statisch machen?

Ich habe hier eine Funktion aus einer anderen Programmiersprache -->


FUNCTION Zufall STATIC

Anzahl = Anzahl + 1

IF Anzahl = 1 THEN

z = 13

a = 513

c = 29741096258473

p = 2 ^ 48

END IF

g = INT((a * z + c) / p)

z = (a * z + c) - g * p

Zufall = z / p

END FUNCTION


Es soll jetzt nicht darum gehen, ob das eine herrliche Funktion ist, oder ob man das besser programmieren kann oder nicht !!

  • Bei dieser Programmiersprache ist es so, dass alle Variablen innerhalb einer Funktion lokale Variablen sind, die außerhalb der jeweiligen Funktion keinerlei Einfluss, Wert, oder Bedeutung haben, es sei denn man definiert es absichtlich so.

  • Bei dieser Programmiersprache ist es so, dass das Kommando "STATIC" dafür sorgt, dass ALLE Variablen innerhalb der Funktion lokal statisch sind, d.h. dass ihr Variablenwert bei mehrfachen Aufrufen derselben Funktion nicht auf Null zurückgesetzt wird, sondern gemerkt wird und erhalten bleibt. Man kann in dieser Programmiersprache zwar auch einzelne Variablen statisch machen, anstatt alle auf einmal, aber das soll jetzt mal nicht weiter interessieren.


  • Wie macht man Variablen in Python 3.4 innerhalb einer Funktion lokal statisch OHNE sie global machen zu müssen ? Alle Variablen dürfen nicht auf Null zurückgesetzt werden, sondern ihr Wert muss bis zum nächsten Aufruf der Funktion gemerkt werden, weil es eine Art iterativer Prozess ist, die Variablen innerhalb der Funktion sollen aber nicht außerhalb der Funktion wirksam sein bzw. "herumgeistern", eben NICHT global sein.

  • Rückgabewert dieser Funktion ist Zufall = z / p. In dieser Programmiersprache ist es so, dass der Name des Rückgabewertes dem Namen der Funktion entsprechen muss, aber das ist nicht so wichtig !

  • Ist dieses Programmierkonzept überhaupt in Python möglich ?

  • Wie müsste diese kleine Mini-Funktion in Python-Programmtext geschrieben aussehen ?

P.S. --> Dies ist keine Hausaufgabe, und ich bin kein Schüler oder ähnlicher Schwachsinn und die Internetrecherche hat mich nicht in die Lage versetzt eine lauffähige Funktion zu programmieren die dasselbe tut, was diese Funktion von oben tut !

Hilfreichste Antwort - ausgezeichnet vom Fragesteller
von darkshadow582, 60

Ich persönlich kenne mich mit Python nicht direkt aus, aber ich verstehe nicht was das Problem wenn die Variablen Global wären, aber wenn das nicht geht gibt es villeicht die Option den Inhalt der Lokalen Variablen in andere Globale Variablen zu speichern?

Kommentar von DepravedGirl ,

Vielen Dank für deine Antwort !

Wie es scheint muss ich weiter herumexperimentieren.

Antwort
von spaghetticode, 55

Soweit mir bekannt, lässt sich das in Python nur über eine globale Variable bewerkstelligen. Aber globale Variablen will man nicht.

Gibt es dafür einen bestimmten Anwendungsfall? Oder willst du nur wissen, ob das geht? Mir fällt eigentlich kein Anwendungsfall ein, in dem man das nicht mit der besseren Lösung "Parameter-Rückgabewert" nachbilden kann.

Kommentar von DepravedGirl ,

Erst mal vielen Dank für deinen Antwort !

Mir geht es darum die in meiner Frage abgelistete Funktion in Python nachzubilden.

Antwort
von TeeTier, 47

Das geht mit Python so direkt nicht, aber du kannst dir einen Funktor drum herum bauen, und dann einfach das Objekt direkt aufrufen.

Diese Lösung wäre auch im Bezug auf Multitasking empfehlenswert!

Aber wie auch immer ... wenn du nicht von alleine auf die Lösung kommst, dann fehlen dir offensichtlich noch zu viele Grundlagen, also fang erst mal damit an! :)

Viel Erfolg! :)

Kommentar von DepravedGirl ,

Vielen Dank für deine Antwort !

Antwort
von DepravedGirl, 36

Nach langem suchen im Internet habe ich nun eine Lösung gefunden.

Diese Webseite habe ich gefunden -->

http://edumaven.com/python-programming/static-variable

Zitat von dieser Webseite -->

There are no function-level static variables in Python, but you can fake it quite easily.

-----------------------------------------------------------------------------------------------------

Mit Hilfe dieser Webseite konnte ich nun meine Funktion aus QBasic / QB64 umschreiben in Python -->

Kommentar von DepravedGirl ,

Diese in Python geschriebene Funktion tut zu 100 % identisch das, was dieselbe Funktion und QBasic / QB64 geleistet hat.

Kommentar von ralphdieter ,

Man lernt nie aus: Dass eine Funktion wie jedes andere Objekt ein __dict__ enthält, überrascht mich nicht. Aber dass es beschreibbar ist und für solche Zwecke benutzt werden darf, musste ich erst in der offiziellen Python Language Reference (https://docs.python.org/2/reference/index.html) nachlesen. Und die gibt grünes Licht!

Antwort
von ralphdieter, 18

Python kennt keine globalen Variablen. Jede Variable liegt in einer Klasse, Instanz, Funktion oder einem Modul. "global==böse" gilt damit nicht mehr.

Du hast ja inzwischen selbst eine Lösung für Dein Problem gefunden. Deshalb will hier nur ein paar Möglichkeiten aufzählen, wie man es auch machen kann.

Zur Vereinfachung nehme ich eine Funktion z(), die die Gesamtzahl ihrer Aufrufe zurückgeben soll, also nacheinander 1, 2, 3, usw.:

1. als Modul

Ein Python-Programmierer würde Deine Funktion in ein Modul packen:

__all__ = ( z, )

a = 0

def z():
 a += 1
 return a

So wird das benutzt:

from z import z

z()

2. als Instanz einer Klasse

Das willst Du vermutlich nicht haben, aber der Vollständigkeit wegen:

class Z(object):
def __init__(self):
self.a = 0

def __call__(self):
 self.a += 1
 return self.a

z = Z()

So wird das benutzt:

z()

Die Besonderheit dabei: Man kann leicht mehrere unabhängige Zählfunktionen erzeugen: z2=Z(); z2().

Als Alternative könnte a auch als Klassenvariable existieren:

class Z(object):
a = 0

@staticmethod
def z():
 Z.a += 1
 return Z.a

So wird das benutzt:

Z.z()

3. als (Meta-)Klasse

Die Formulierung Z.z kann man umgehen, indem man den Konstruktor umdefiniert:

class z(object):
a = 0

def __new__(cls):
 cls.a += 1
 return cls.a

So wird das benutzt:

z()

4. als Funktion

Eine Funktion kann — wie jedes Objekt — Variable und Methoden enthalten. Das Problem dabei: Sie werden nicht automatisch initialisiert. Mir fallen vier Wege ein, das zu lösen:

def z():
if 'a' not in z.__dict__:
a = 0

z.a += 1
return z.a

Hier wird in jedem Aufruf geprüft, ob initialisiert werden muss.

def z():
try:
z.a += 1
except AttributeError:
z.a = 1

return z.a

Hier wird die Initialisierung als Ausnahme behandelt.

def z(static = {'a':0}):
static['a'] += 1
return static['a']

Hier wird die einmalige Initialisierung für default-Argumente missbraucht.

def z():
z.a += 1
return z.a

z.a = 0

Hier erfolgt die Initialisierung explizit nach der Definition.

Alle Fälle werden so benutzt:

z()

5. Fazit

Eigentlich wären statische Variablen am besten direkt in der Funktion selbst aufgehoben. Leider wird das von Python nicht wirklich unterstützt.

Auch wenn man das mit wenig Code selbst erledigen kann, bleibt alles doch nur ein übler Hack ("ein guter Programmierer kann in jeder Sprache FORTRAN programmieren").

Ich denke, dass ein Modul die einfachste, sicherste und verständlichste Implementierung darstellt. Alles andere ist nicht wirklich Python.

Kommentar von DepravedGirl ,

Recht herzlichen Dank für deine Antwort !

Keine passende Antwort gefunden?

Fragen Sie die Community