我是Python的新手,我正在尝试使用不同包中不同模块的包中的模块的全局计数器。我想要做的是在模块中声明一个变量并将其导入到不同包中的其他模块。我对这个问题做了一个简单的测试,它也在这里发生。我将所有文件放在同一个目录中(它们现在位于同一个包中,但问题是相同的)。
文件glbcntmod.py:
glbcnt = 0
文件glbfuncmod.py:
from glbcntmod import glbcnt
def glbfunc():
global glbcnt
print 'glbcnt = ',glbcnt
file:test.py
#!/usr/bin/env python
from glbcntmod import glbcnt
from glbfuncmod import glbfunc
loccnt = 0
def localfunc():
print 'loccnt = ',loccnt
if __name__ == '__main__':
glbcnt = 0
for i in xrange(0,4):
glbfunc()
localfunc()
glbcnt += 1
loccnt += 1
当我运行test.py时,结果如下所示。 loccnt正在递增,但glbcnt始终为0.问题是什么?
glbcnt = 0
loccnt = 0
glbcnt = 0
loccnt = 1
glbcnt = 0
loccnt = 2
glbcnt = 0
loccnt = 3
答案 0 :(得分:2)
执行此操作的方法是将模块保留在变量作为参考的位置:
counter
如果您在任何地方使用from othermodule import counter
counter = 1
,那么它将在模块之间具有合理的价值。
这是因为每次在Python中对名称进行赋值时,与该名称关联的对象都会更改 -
也就是说,如果你这样做
counter
您的{{1}}变量将指向与该分配不同的对象。由于数字是不可变对象,因此甚至存在其他问题。
但是你保留原始模块,你正在改变该模块对象中的一个属性 - 其行为与任何其他Python对象完全相同。只要其他代码将变量作为模块的属性进行访问,您就可以了。
答案 1 :(得分:2)
请注意int
在python中是不可变的。这意味着做一些像
a = 0
b = a # b = 0
b += 1 # b = 2
仍将a
保留为0
。
执行from glbcntmod import glbcnt
时,这基本上等于
import glbcntmod
glbcnt = glbcntmod.glbcnt
因此,如果您再增加glbcnt
,则只会为本地名称分配新值。原始glbcnt
未更改。
如果要使用全局变量,则必须使用其全局名称。所以你想要使用和修改的是glbcntmod.glbcnt
。
答案 2 :(得分:1)
如果您尝试从其他模块更新全局变量,请查看以下答案:https://stackoverflow.com/a/15595447/3224629
答案 3 :(得分:1)
在test.py中:
if __name__ == '__main__':
glbcnt = 0
for i in xrange(0,4):
...
glbcnt += 1
你在这里创建一个局部glbcnt变量,这是一个增加的变量。你的glbfunc()没有看到这个变量,因此无法打印它的值。
试试这个:
if __name__ == '__main__':
global glbcnt
glbcnt = 0
...
另外,因此,你的整个glbcntmod.py文件变得毫无意义。
这不是因为变量被声明为全局一次,它变得全局无处不在。
“global glbcnt”只是意味着从这里开始,在这个范围内,对glbcnt的任何引用都将引用全局变量。没有任何效果适用于其他范围,即。其他模块。