2016-10-06 5 views
0

Ich habe eine Funktion fun(), die einen Callback callback() bindet, wenn eine Matplotlib Abbildung angeklickt wird. Ich möchte, dass dieser Callback auf den Variablenbereich fun() zugreifen kann, um Änderungen vorzunehmen. Wie kann ich das tun?Python Callback Variable Bereich

import numpy as np 
import matplotlib.pyplot as plt 

def callback(event): 
    data = event.xdata 

def fun(): 
    data = 0 

    fig, ax = plt.subplots() 
    ax.plot(np.random.rand(12), np.random.rand(12), 'go') 
    fig.canvas.mpl_connect('button_release_event', callback) 

    plt.show() 
    return data 

print fun() 

Putting data im global Umfang ist keine akzeptable Lösung. Die Funktion sollte eigenständig sein. Die Antwort here würde mir erlauben, Variablen an callback() zu übergeben, aber ließ mich sie nicht bearbeiten.

+0

Verwenden Sie eine geschachtelte Funktion (definieren Sie Ihren Rückruf im Körper von Spaß). Beachten Sie jedoch, dass die Fun-Funktion bereits beendet wurde, wenn Ihr Callback aufgerufen wird. –

+0

Ich habe bereits eine verschachtelte Funktion in '' 'fun()' '' versucht: es funktioniert nicht. Ein geschachtelter '' 'Callback()' '' kann auf den Bereich von '' 'fun()' '' zugreifen, aber er kann ihn nicht verändern. Probieren Sie es selbst aus. Außerdem wird die Funktion normalerweise erst beendet, wenn '' 'plt.show()' '' gelöst ist (d. H. Nach einer Canvas-Interaktion). Ich habe keine Probleme mit vorzeitiger Beendigung im obigen Skript. – SkyNT

+0

In der Tat können Sie mit einem kleinen Trick. Siehe http://stackoverflow.com/questions/6198709/how-do-i-change-nesting-functions-variable-in-the-nested-function. Sie können ein dict wie d = dict (data = 0) verwenden und dann d ["data"] in der verschachtelten Funktion ändern. –

Antwort

1

Ich verstehe, dass Sie einige Status haben möchten, die während der Laufzeit geändert werden können. Eine Option könnte sein, ein aufrufbare Objekt zu verwenden, das ist keine Funktion (ich habe es nicht getestet):

class Callback(object): 
    def __init__(self, data): 
     self.data = data 
    def __call__(self, event): 
     # Manipulate the data 
     self.data += 1 
... 
datacallback = Callback(0) 
fig.canvas.mpl_connect('button_release_event', datacallback) 
print datacallback.data 

diese Weise können wir einen Zähler haben würden, wie oft das Ereignis ausgelöst wird. Aber es funktioniert mit jeder Art von Daten, auch komplexer als eine ganze Zahl.

+0

Ich habe es gerade getestet und es funktioniert. Dies löst mein Problem. – SkyNT