Python函数中返回的变量工作不正常
我一直在尝试在变量中的函数中返回一个变量,并在其外部使用它:Python函数中返回的变量工作不正常,python,variables,return-value,Python,Variables,Return Value,我一直在尝试在变量中的函数中返回一个变量,并在其外部使用它: test = 0 def testing(): test = 1 return test testing() print(test) 但当我运行它时,结果是0。我怎样才能解决这个问题?您的作用域和/或分配有点混乱。试试这个: def testing(): test = 1 return test test = testing() print(test) 说明:模块内部的测试与测试不同。您必须在
test = 0
def testing():
test = 1
return test
testing()
print(test)
但当我运行它时,结果是0。我怎样才能解决这个问题?您的作用域和/或分配有点混乱。试试这个:
def testing():
test = 1
return test
test = testing()
print(test)
说明:模块内部的
测试与测试不同。您必须在模块级别分配它以获得预期结果。因为您在函数中声明了test
,所以它不是一个全局变量,因此,您无法访问在函数外部创建的变量test
,因为它们是不同的作用域
如果要将test
返回到变量,则必须执行以下操作
result = testing()
print(result)
或者,您也可以添加全局
语句:
test = 0
def testing():
global test
test = 1
return test
testing()
print(test)
顺便说一句,在执行条件语句时,您不需要在函数testing()
中的1==1=/code>:)周围加括号。在函数testing()
中,您正在创建一个新变量test
,而不是指已经存在的变量。如果要执行此操作,应在顶部使用global
语句,如中所示:
def testing():
global test
...etc...
函数中的test
变量没有全局范围。因此,如果要将返回值存储在变量中并在其后输出,可以执行以下操作:
result = testing()
print(result)
# we already can define testing here
# it is overwritten later on, then
def testing():
# all names we use inside of testing are gone at the end
# if we just want a value, we can skip temporary names
return 1
# store the return value of testing() for later use
test = testing()
print(test)
TLDR:返回值
必须分配给呼叫站点上的某个对象
test = testing()
Python中的函数有自己的作用域。它在进入(调用)函数时创建,在离开函数时销毁。分配给作用域内的名称会使该名称成为该作用域的本地名称,从而导致该名称与作用域一起被销毁
# start outer scope
test = 0 # create name outer:test
def testing():
# start inner scope
test = 1 # create name outer.testing:test
return test
# end inner scope
# destroy name outer.testing:test
testing() # new temporary inner scope outer.testing
print(test) # use name outer:test
# end outer scope
值得注意的是,内部作用域中的名称可以是外部作用域中的“”名称。虽然名称test
存在于testing
和外部作用域中,它指的不是同一事物。这有两个重要影响:
内部测试的分配不影响外部测试
在测试
结束时,内部测试
被销毁,只剩下外部测试
这就是调用testing()
没有达到预期效果的原因:它从不修改传递给print
的外部test
它不返回名称,只返回指向的值
def testing():
test = 1 # test refers to the value 1
return test # return test => value 1
函数返回的值与任何其他值类似——可以是来自文本、查找或其他。最重要的是,除非将该值指定给名称或直接使用,否则该值不会持久存在
testing() # call test, discard its value
test = testing() # call test, store its value as `test`
print(testing()) # call test, use its value in `print`
因此,为了从函数返回某些内容供以后使用,必须将结果存储到名称中。然后可以在以后的语句中使用该名称。您的案例的一个简单示例如下所示:
result = testing()
print(result)
# we already can define testing here
# it is overwritten later on, then
def testing():
# all names we use inside of testing are gone at the end
# if we just want a value, we can skip temporary names
return 1
# store the return value of testing() for later use
test = testing()
print(test)
附录:函数可以修改其包含范围。但是,名称必须显式声明为来自外部作用域
和关键字允许修改外部作用域中的名称。非本地
是最接近匹配功能范围的名称。global
是模块作用域中的名称,而不考虑其间的任何函数
test = 0
def increment():
global test # declare test as belonging to a specific scope
test += 1
# no need to return something
# we already modified the outer `test`
print(test) # 0
increment()
print(test) # 1
请注意,修改外部名称通常是反模式的标志,global
s比nonlocal
s更重要。除了小脚本之外,很难跟踪访问和修改global
s的内容。通常,使用类或生成器保存状态更合适
函数始终可以从其包含范围中读取名称,前提是它从不写入相同的名称。这样的文件很容易创建,并且缺少修改使它们更容易跟踪。请注意,除非声明为全局
或非局部
,否则修改函数中任何位置的名称都会使其成为局部的:
test = 0
def increment():
global test
test += 1
def show_test():
# we never modify `test`, so it is fetched from the outside
print(test)
def show_and_increment1(): # this function is broken!
print(test) # `test` is *not* the outer one, since we modify it in the function
test += 1 # modifying `test` makes it local for the *entire* function
def show_and_increment2(): # this function works!
global test # force `test` to be global
print(test)
test += 1
show_test() # 0
increment()
show_test() # 1
show_and_increment2() # 1
show_and_increment2() # 2
show_and_increment2() # 3
show_test() # 4
show_and_increment1() # UnboundLocalError: local variable 'test' referenced before assignment
将全局变量test
的名称更改为g_test
,您就会明白。他们是两个完全不同的变量,使用同一个名字,你只是把自己弄糊涂了。在写这篇文章的时候,有7票支持一个看起来正确的答案。但我认为没有人真正解释过这一点。代码中真正的问题(它不起作用的唯一原因)是,在执行函数调用时,没有捕获返回值。然后打印一个原始的未更改的全局变量。关于范围的评论是正确的。函数中的“test”是局部作用域,它是一个不会更改函数外部的全局“test”变量的副本。但是,如果您是Python新手,您应该在google上搜索“mutating vs nonmutating”当您处理列表并从看似相似的代码中获得不同的行为时,请阅读有关堆栈溢出的帖子。如果您通过了作为参数的“test”,您仍然必须返回它并捕获它才能工作。但对于列表等变量的变异,这种行为是不同的。除了其他人已经为您的问题提供的代码修复之外,希望您觉得这有帮助。oops-这是一篇3年前的文章。我想我写这篇文章是为了给那些在寻找解决问题时偶然发现这条线索的人提供完整性。谢谢你。我有一段更为复杂的代码,其中包含递归,显然由于同样的原因失败了。只是很难看到所有代码的内部。我想,这个简单的问题和答案可能让我找到了解决方案。:-)这也很有用,但另一个答案强调了代码中可能存在的错误(没有捕获返回值),因此它作为一个解决方案具有更广泛的含义,并且更有可能帮助海报找到可能导致此示例的真实代码中的错误。作为Python新手,我还没有意识到你可以做你答案中的事情,这可能会帮助我处理其他用例,所以谢谢你的帖子。