Seite 1 von 1
Problem mit exec innerhalb einer Funktion
Verfasst: Mittwoch 9. Juli 2003, 16:07
von Kartoffel
Also, ich habe folgende Funktion:
Sie wird ausgeführt, wenn ich einen Text in ein Tkinter-Entry-Feld eingegeben habe und die Return-Taste drücke.
Mein Problem ist folgendes: Der eingegebene Programmcode wird zwar ausgeführt, aber die Variablen, die ich darin definiert habe, gehen verloren, d.h. sie sind nachher nicht mehr vorhanden.
Ich vermute mal, dass es daran liegt, dass die Objekte im Namensraum der Funktion erstellt werden und darum beim Beenden des Funktionsdurchlaufs wieder gelöscht werden.
Ich hab aber keine Ahnung, wie ich das ändern kann, hat jemand ne Idee?
Verfasst: Mittwoch 9. Juli 2003, 16:42
von rAiNm4n
Kartoffel hat geschrieben:
Ich vermute mal, dass es daran liegt, dass die Objekte im Namensraum der Funktion erstellt werden und darum beim Beenden des Funktionsdurchlaufs wieder gelöscht werden.
Genau, Also musst du die Variablen aus dem lokalen Namensraum der Funktion in den globalen Namesnraum übertragen.
Code: Alles auswählen
import sys
def einlesen(x):
exec x.widget.get()
namespace = locals() # speichert alle lokalen Namen in Form eines Dictionaries in namespace
for varname in namespace.keys():
setattr(sys.modules["__main__"], varname, namespace[varname])
# sys.modules ist ein Dictionary aller Module und __main__ ist immer das Hauptmodul (dein Skript)
Ist zwar etwas umständlich, aber es funktioniert auf jeden Fall...
cu
Chris
Verfasst: Mittwoch 9. Juli 2003, 20:05
von Milan
Hi, eine Globale Variable mit "global" definieren geht auch

Nur eine Frage:
x.widget.get() ist doch ein Funktionsruf, oder? Wofür brauchst du hier exec?

Verfasst: Mittwoch 9. Juli 2003, 21:48
von Voges
Milan hat geschrieben:Nur eine Frage:
x.widget.get() ist doch ein Funktionsruf, oder? Wofür brauchst du hier exec?

Nicht get() wird mit exec ausgeführt, sondern das, was get() zurückliefert, also den Inhalt des Entry-Widgets. Ich hab' mal
global a; a = 42 eingegeben und nach Return dann
print a. Hat funktioniert! Spaßige Sache

Jan
Verfasst: Donnerstag 10. Juli 2003, 07:45
von Milan
Danke Voges, hatte ich glatt vergessen.

Ich glaube aber, das rainmans Lösung besser doch ist, weil ja nicht bekannt ist, wie die gloabale(n) Variablen heißen müssen, sie werden ja dynamisch erzeugt. Man könnte höchstens das machen:
Code: Alles auswählen
def einlesen(x):
exec x.widget.get()
global ergebnisse
ergebnisse=locals()
Jetzt stünden alle Variablen deiner Funktion in ergebnisse (Dictionary!) und sind per Definition auch global nutzbar (also außerhalb deiner Funktion).
Verfasst: Freitag 11. Juli 2003, 18:34
von Kartoffel
Hm, nette Versuche. Inzwischen hab ich aber selbst einen viel einfacheren Weg gefunden:
exec code in globals()
führt den string Code mit globals als globalen und lokalen Namensraum aus.
Ist doch manchmal gut, die mitgelieferte Doku zu lesen, auch wenn sie nicht sehr übersichtlic ist...