Seite 1 von 1
Aufrufekontext einer Funktion
Verfasst: Freitag 23. Juli 2010, 13:17
von Goswin
Wie kann eine Funktion wissen, von welchem Namescope aus sie aufgerufen wurde?
Die mit Abstand wichtigste (dh häufigst aufgerufene) Funktion, die ich je progammiert habe, ist
Code: Alles auswählen
def display(*expr_lst):
"""
Function programmed for Python 3.1:
Shows expressions together with their values.
"""
for (nz,expr) in enumerate(expr_lst):
print("{} = {}".format( expr.strip(), eval(expr,globals()) ),end='')
if nz<len(expr_lst)-1: print(', ',end='')
print()
aufzurufen wie beispielsweise in:
Leider kann ich sie nicht an einer zentralen Stelle aufbewahren und importieren, sondern muss sie in alle meine Module explizit hineinkopieren, sonst kennt sie nicht alle Objekte der Ausdrücke, die sie auswerten soll. Wie übergebe ich den richtigen Kontext an eval(), oder ist so etwas gar nicht möglich?
Re: Aufrufekontext einer Funktion
Verfasst: Freitag 23. Juli 2010, 13:34
von Hyperion
Re: Aufrufekontext einer Funktion
Verfasst: Freitag 23. Juli 2010, 13:50
von lunar
Mit "inspect.currentframe()" kommst Du an den aktuellen Stackframe. Darüber kommst Du an den Aufrufer (einfach eine Frame höher) und iirc auch dessen Namensraum. Das ist allerdings schon sehr schwarze Magie und hat in Produktivcode eigentlich nichts zu suchen.
Re: Aufrufekontext einer Funktion
Verfasst: Freitag 23. Juli 2010, 17:42
von Goswin

Problem gelöst

.
An
lunar geht mein Dank für den Hinweis auf das <inspect>-Modul. Mit inspect.currentframe() konnte ich zwar nichts anfangen, aber das Modul hat ja noch andere interessante Funktionen.
Meine nun angepasste Funktion ist jetzt:
Code: Alles auswählen
import inspect
def display(*expr_lst):
"""
Function programmed for Python 3.1:
Shows expressions together with their values.
"""
_globals_dict = inspect.stack()[1][0].f_globals
for (nz,expr) in enumerate(expr_lst):
print("{} = {}".format(expr.strip(),eval(expr,_globals_dict)),end='')
if nz<len(expr_lst)-1: print(', ',end='')
print()
Re: Aufrufekontext einer Funktion
Verfasst: Freitag 23. Juli 2010, 17:57
von ms4py
Die Frage ist doch, zu was man so etwas überhaupt braucht, ich vermute mal zum Debuggen?! Schon mal was von interaktivem Debuggen gehört... Grausamer Code...
Re: Aufrufekontext einer Funktion
Verfasst: Montag 26. Juli 2010, 15:08
von Goswin
ms4py hat geschrieben:Die Frage ist doch, zu was man so etwas überhaupt braucht, ich vermute mal zum Debuggen?! Schon mal was von interaktivem Debuggen gehört... Grausamer Code...
@
ms4py: Wenn ich einen Fehler suche, dann drucke ich solange Zwischenergebnisse aus, bis ich entdeckt habe, wo der Fehler liegt: das ist doch wohl interaktiv, oder

? Bisher war ich mit solchem Debuggen ziemlich erfolgreich; darüber hinaus habe ich nicht den blassesten Dunstschimmer einer Ahnung, was mit interaktivem Debuggen gemeint sein soll, kommt mir vor wie
deep black magic, auf der Uni haben wir so etwas nie durchgenommen. (Ich bin kein Informatiker, habe aber gehört, Python soll gerade für Nichtinformatiker gut sein). Muss man erst technisches "Interaktives Debuggen" können, um in Python zu programmieren?
Nachtrag: Von ms(=microsoft?) habe ich schon einmal gehört, habe aber noch nie im Leben auf so einem Betriebssystem programmiert, hat das ganze etwas mit Windows zu tun? Ich möchte
nicht agressiv wirken, nur einige Stereotypen untergraben. Es ist erstaunlich, was einige naive Informatiker bei Laien so alles an Fachkenntnissen voraussetzen...
Re: Aufrufekontext einer Funktion
Verfasst: Montag 26. Juli 2010, 15:33
von cofi
ms4py meint damit wohl Debugger(sind die nicht immer interaktiv oder hab ich da was verpasst?), zb
pdb
Hab ein Herz fuer Baeume!

Re: Aufrufekontext einer Funktion
Verfasst: Montag 26. Juli 2010, 16:29
von ms4py
cofi hat geschrieben:ms4py meint damit wohl Debugger(sind die nicht immer interaktiv oder hab ich da was verpasst?), zb
pdb
Hab ein Herz fuer Baeume!

Ja, ich meinte Debugger. Die sind vermutlich auch alle interaktiv. Nur das Debuggen ist nicht immer interaktiv (s. Beschreibung vom OP

).
Und ja, am Debuggen mit Prints ist i.d.R. auch nichts auszusetzen, allerdings sollte man dann eine überschaubare Menge (max. 5 - 10) von diesen Statements haben, um dann auch zuordnen zu können, an welcher Stelle jetzt was ausgegeben wurde. Dann braucht man auch nicht auf solche dirty Hacks zurückzugreifen, um die Expression noch mit ausgeben zu können.
Das Schlimme an dieser Vorgehensweise sind eben die Nebeneffekte, die man IMO nicht exakt abschätzen kann. Ich würde mich nicht 100% darauf verlassen, dass der evaluierte Ausdruck wirklich derselbe ist wie der im lokalen Kontext.
Re: Aufrufekontext einer Funktion
Verfasst: Montag 26. Juli 2010, 16:41
von lunar
@Goswin: Interpretiere nicht mehr in Beiträge hinein, als drin steht. Du musst keine Debugger verwenden können, um Python zu programmieren. Letztlich musst Du außer einem Editor und ein bisschen Grundkenntnissen in der Bedienung Deines Systems gar nichts können ... es ist nur einfach hilfreich, wenn man einen Debugger verwenden kann (wobei man ihn in Python tatsächlich selten benötigt). Und wenn Du anfängst, mit schwärzester Magie (nichts anderes ist der Ansatz über "inspect") Debugging-Funktionen zu bauen, dann habe ich als Programmierer einfach das Gefühl, dass Du Dir zu viel Arbeit machst und zu umständliche Lösungen suchst. ms4py ging es wohl nicht anders, daher sein Kommentar.
Mit "naiven Informatikern" hat das im Übrigen einfach mal gar nichts zu tun. Insofern ist die "ich bin doch nur Laie"-Einstellung – bei allem gebührenden Respekt – recht lächerlich. Informatik ist eine Wissenschaft, die Bedienung eines Debuggers dagegen nicht. Debuggen ist eine grundlegende handwerkliche Fähigkeit eines Programmierers, und für die Informatik allenfalls peripher relevant. Die Bedienung eines Debuggers lernt man nicht im Informatik-Studium, sondern durch Eigeninitiative und das Lesen von Dokumentation, und das kann auch ein Laie.