1

我在一个文件中构建了一个相当大的程序。文件的大小使其无法使用,因此我决定拆分为多个模块,但此后一直对变量范围感到头疼。我已经在很大程度上修复了它(在此过程中进行了相当多的学习),但我很想了解良好的结构,以避免将来通过艰难的方式学到的教训。有几个具体点,但也欢迎一般建议。

需要共享相同命名空间的模块

我有两个似乎需要共享同一个命名空间的模块。一个是程序的主流程(它与对象之间传输数据,并调用 UI),另一个是 UI(响应用户输入,调用主流程)。

这些模块中的每一个是否应该导入另一个,然后主文件同时导入?这对我来说似乎不是特别优雅。

从 [模块名称] 导入 *

在这个问题的答案中:

Python:在模块和类之间共享全局变量

有一个建议from [modulename] import *应该避免。

可以from [modulename] import *一起构建只有类定义的大量模块吗?什么是“安全”用例?

4

1 回答 1

1

需要访问彼此命名空间的模块与需要共享相同命名空间的模块不同。我想不出任何你可以用from modulename import *你做不到的事情import modulename。你只需要在你的很多名字前加上modulename.那是好事,不是坏事。它使您的代码自我记录,这就是from modulename import *要避免的原因。

您可以让 UI 和主要流程模块相互导入。遇到问题的唯一方法是在函数范围之外引用它们之间的名称。例如

# mainflow.py
import ui # interpreter stops reading mainflow and starts reading ui

class Foo:
    ...

theUI = ui.UI()

# ui.py
import mainflow # mainflow already being loaded; interpretation of ui continues uninterrupted

def dosomething():
    myfoo = mainflow.Foo() # so far so good, not interpreted until the function is called

class Bar(mainflow.Foo): # mainflow.Foo not reached yet, error here
    ...

class UI:
    ...

另一方面,如果 ui 恰好首先被导入,那么theUI = ui.UI()当所有主流都已被解释但 ui 仅被解释为import mainflow. 但是,只要将所有相互引用的内容都放在函数中,就可以相处得很好。例如

# mainflow.py
import ui
...

theUI = None

def initialize():
    global theUI
    theUI = ui.UI()

类之间的依赖仍然存在问题;我建议你不要这样做。但如果你这样做了,你可以用这种奇怪的方法来完成整个事情:

# mainflow.py
...

theUI = None

def initialize():
    global theUI
    theUI = ui.UI()

import ui # Waht!? Crazy! Import at the bottom of a file. Now all of mainflow's names are guaranteed to exist and ui can access them.

现在有了 ui.py 的第一个版本和 mainflow.py 的最后一个版本,程序将编译并运行。我真的不推荐上述内容;更好地组织你的代码,这样你就没有这样的依赖。但是,如果您所拥有的只是在模块中的函数之间来回调用,您就不必求助于这些技巧。

有更多面向对象的设计方法可以使您的 UI 和您的程序流程不直接相互依赖,但是这样的重新设计将比仅仅复制和粘贴到文件和前缀名称更复杂,module.我认为您不想这样做除非您有特定原因,否则您的重新设计过度。

于 2013-06-02T18:49:45.490 回答