如果代码被拆分成不同的文件,我真的不明白python如何处理全局变量。
假设我有3个文件:class1.py,class2.py,main.py
在main.py中我定义了一个全局变量
from class1 import Class1
from class2 import Class2
global sys
sys = constructor()
此对象包含有关我模拟的系统的信息,并由class1.py和class2.py中定义的类使用和操作。
当然可以说这是一种糟糕的风格,应该避免利用像这样的全局变量,但这不是重点。
如果现在我在任一类中使用sys,那么它是未知的。要使用全局变量,当然可以在某处定义它们然后包含此文件。但是,这些类所做的更改不会相互影响,所以我不想这样做。
另一种方法是定义一个新的Class SuperClass,其中sys是一个成员。如果现在Class1和Class2继承自SuperClass,我可能会用super关键字做一些事情。我真的不想这样做......
长话短说...有没有办法定义一个python对象,它的行为类似于C风格的全局变量?
如果我举一个例子,也许会有所帮助:
答案 0 :(得分:0)
不,没有办法拥有“C风格的全局变量”,这是设计的。在实例化时,将您的sys对象明确地传递给Class1和Class2,并且您将完成,并且具有干净,可读,可测试,可维护的实现:
# lib.py
class Class1(object):
def __init__(self, sys, whatever):
self.sys = sys
# ...
class Class2(object):
def __init__(self, sys, whateverelse):
self.sys = sys
# ...
# main.py
from lib import Class1, Class2
def main():
sys = constructor()
c1 = Class1(sys, 42)
c2 = Class(sys, "spam")
# now you can work with c1 and c2
if __name__ == "__main__":
main()
回答你的第一个问题:
我真的不明白python如何处理全局变量 代码被分成不同的文件。
Python的“全局”是模块级名称。在运行时,模块是对象(module
类型的实例),在模块顶层定义的所有名称都成为模块实例的属性 - “已定义”是通过赋值,def
或class
语句或import
语句。
在模块中,顶级名称可以通过所有模块代码中的非限定名称访问 - 如果要重新绑定顶级,则只需要global
关键字在函数中命名。
从模块外部,您可以使用限定路径访问这些名称,即如果module1
定义名称foo
,您可以通过导入module2
从module1
访问该名称(使module1
中的module2
顶级名称并使用通常的属性解析(dotted.name)语法。
您还可以使用foo
直接导入from module1 import foo
,在这种情况下,将在foo
中创建一个新名称module2
并绑定到module1.foo
(更多确切地说:绑定到此时绑定到module1.foo
)的对象。这里的要点是你知道在两个不同的命名空间中有两个不同的名称,因此重新绑定只会影响它反弹的命名空间。
你当然想阅读Ned Batcheler's famous article on Python's names,这通常是理解这一切的好起点。