Tkinter自定义类调用__init__变量触发AttributeError的解决方法
报错原因
你遇到的AttributeError根源是回调函数绑定方式错误:
- 你给OptionMenu传入的回调是
Schedule.selectPG,这是类层面的未绑定方法,不会自动关联当前类实例。Tkinter在触发OptionMenu的command回调时,会自动把当前选中的选项字符串作为第一个参数传入,此时方法里定义的self形参实际接收到的就是这个字符串,访问self.tree自然会抛出'str' object has no attribute 'tree'错误。 - 初始化时直接调用
self.selectPG()能正常运行,是因为这是实例方法调用,会自动把类实例绑定到self参数,没有传参错位问题。 - 另外你的代码还存在三个隐藏bug:一是创建OptionMenu时引用了从未定义的
self.optionsFrame,二是selectPG方法里依赖的全局变量PGselectionint从未赋值,三是Treeview组件创建后没有调用pack/grid/place布局,无法正常显示。
修复步骤
- 补全
self.optionsFrame组件的初始化和布局代码,放在创建OptionMenu之前 - 将OptionMenu的command参数从
Schedule.selectPG改为实例方法self.selectPG,确保回调能正确关联当前类实例 - 给
selectPG方法增加可变参数接收Tkinter自动传入的选项值,避免参数数量不匹配报错 - 移除对未初始化全局变量
PGselectionint的依赖,直接根据StringVar存储的选中值反查对应的分组索引 - 补全Treeview组件的布局代码,同时增加列标题配置逻辑,确保表格正常显示
修正后可运行代码
from tkinter import * # 原有全局变量定义,可根据实际业务替换 ProduktionsGruppe = {0: "Gruppe 1", 1: "Gruppe 2", 2: "Gruppe 3"} listofnumberlists = { 0: ["Mitarbeiter", "Schicht", "Aufgabe"], 1: ["Maschine", "Wartungstermin", "Status"], 2: ["Material", "Bestand", "Liefertermin"] } class Schedule(): def __init__(self, master): self.master = master master.title('Schedule') master.geometry('800x800') self.Main = Frame(self.master) self.Main.pack(fill=BOTH) # 组件初始化 self.optionsFrame = Frame(self.Main) self.optionsFrame.pack(side=TOP, fill=X, padx=10, pady=10) self.treeFrame = Frame(self.Main, height=690, width=800) self.treeFrame.pack(side=BOTTOM, expand=False) self.PGvariable = StringVar() self.PGvariable.set(ProduktionsGruppe[0]) self.ProduktionsGruppeOptionMenu = OptionMenu( self.optionsFrame, self.PGvariable, 'Gruppe auswählen', *ProduktionsGruppe.values(), command=self.selectPG ) self.ProduktionsGruppeOptionMenu.pack(pady=10) self.tree = Treeview(self.treeFrame, show='headings', height=32) self.tree.pack(fill=BOTH, expand=True) # 初始化加载表格 self.selectPG() def selectPG(self, *args): # 清空现有表格内容 for i in self.tree.get_children(): self.tree.delete(i) # 获取当前选中的分组 selected_text = self.PGvariable.get() # 反查分组对应的索引,不再依赖未初始化的全局变量 selected_idx = None for idx, group_name in ProduktionsGruppe.items(): if group_name == selected_text: selected_idx = idx break if selected_idx is None: return # 配置表格列 columns = listofnumberlists[selected_idx] self.tree['columns'] = columns for col in columns: self.tree.heading(col, text=col) self.tree.column(col, width=120, anchor=CENTER) if __name__ == '__main__': root = Tk() Schedule(root) root.mainloop()
内容的提问来源于stack exchange,提问作者BobbyPeace420
相关产品推荐
相关产品推荐

