为何Python中非静态方法形式的事件处理器未执行?附代码
问题原因与修复方案
核心问题:实例被垃圾回收导致非静态方法绑定失效
你创建Setup_IntrctveLgnd实例时,仅执行了Setup_IntrctveLgnd(legend,fig),没有将该实例赋值给任何变量。Python的垃圾回收机制会自动销毁这个无引用的临时实例,而self.nonstatic_onpick是绑定到该实例的方法——实例被销毁后,这个绑定的事件处理器也随之失效,因此点击图例时不会触发它。
而静态方法static_onpick属于类本身,不依赖任何实例存在,所以即便实例被回收,类的静态方法依然能被正常调用。
能否将非静态方法作为事件处理器?
完全可以,只要保证绑定该方法的实例在事件触发时仍然存在即可。
修复代码(保持原有结构)
只需把创建的实例保存到变量中,避免被垃圾回收:
import matplotlib.pyplot as plt class Setup_IntrctveLgnd(): def __init__(self,legend,fig): lgndicons=legend.legend_handles lgndicons[0].set_picker(20) fig.canvas.mpl_connect("pick_event", self.nonstatic_onpick) fig.canvas.mpl_connect("pick_event", Setup_IntrctveLgnd.static_onpick) def nonstatic_onpick(self,event): print("non static event handler method working") def static_onpick(event): print("static event handler method working") fig,ax=plt.subplots() ax.plot([0,1,2,3], label="data") legend=plt.legend() # 将实例保存到变量,避免被垃圾回收 interactive_legend = Setup_IntrctveLgnd(legend,fig) plt.show()
修改后点击图例,终端会输出两行预期的文本。
内容的提问来源于stack exchange,提问作者Hassan Hoque
相关产品推荐
相关产品推荐

