我正在使用python Tkinter设计一个gui程序。我在类结构中开发它,每个类包含一个包含小部件的框架。问题是,一个类需要一个来自另一个类的小部件作为参数,另一个类也是如此。我很困惑如何实例化该类。这是我到目前为止尝试过的代码。
frame1 = infoframe(lambda : frame2.listbox1)
frame2 = scriptframe(frame1.entry1)
每当我调用frame1中需要frame2.listbox1作为参数的函数时,该函数不会将frame2.listbox1识别为列表框。我也试过这段代码:
frame1 = infoframe(None)
frame2 = scriptframe(frame1.entry1)
frame1['object'] = frame2.listbox1
但仍然没有运气。我在课程结构中制作程序,以便程序组织良好,但似乎并不像我想象的那么简单。
答案 0 :(得分:0)
您必须将代码分解为单元,以使单元之间的依赖关系图是非循环的。这可能要求你做一些通常被认为是坏风格的事情。
让我们考虑一下Python如何允许两个模块(如“a”和“b”)相互导入。假设主模块以import a
开头。如果导入代码在检查是否存在sys.modules['a']
之后执行'显而易见的'sys.modules['a'] = module('a', code_of_a)
,则在模块调用返回之前,不会向sys.modules添加任何内容。在返回之前,导入b和b尝试导入a时,sys.modules['a']
将不存在,sys.modules['a'] = module('a', code_of_a)
将重复,依此类推,直到达到递归限制。
为防止这种情况,导入会将模块初始化分为两个阶段。它首先在sys.modules中放置一个几乎为空的模块,类似sys.modules['a'] = module('a')
。然后它调用sys.modules['a'].populate(code_of_a)
之类的东西。暴露未初始化的对象通常被认为是不好的风格,但这里必不可少。这与您尝试过的想法相同。
现在,当导入b时,模块a将具有先前语句定义的任何对象。当b导入a时,它将获得部分初始化的模块a。用户只需安排在import b
之前已经初始化了所需的b,因此将a分成'a_before'和'a_after'会打破依赖循环。将import b
放在文件中间的某个位置会违反PEP8警告,将导入放在顶部,但在其中一个文件中需要相互导入才能工作。
另一种解决方案是将代码从a和b移动到首先初始化的新模块c中。
我希望这能为您提供一些适合您情况的建议。