python变量的作用域取决于变量被赋值的位置,python中,只有当变量在模块,类,函数中定义的时候才会有作用域的概念。一共有四种作用域: 局部作用域, 嵌套作用域, 全局作用域, 内置作用域
理解变量作用域是学习装饰器的关键之一,理解了作用域,也为理解更高级的语法与技术奠定基础。
在函数中创建的变量,是局部变量,当函数被执行时,会创建一个局部作用域,这些局部变量只能在这个作用域内使用,出了这个作用域就无法使用了
def test():
value = 100
print(value)
print(value)
在函数外,就不能再访问value这个变量了,上面的代码执行时会报错
NameError: name 'value' is not defined
原因在于最后一行print语句是在全局作用域里执行的,但这个作用域里没有value这个变量。
def test():
value = 100
def test_2():
value2 = 99
print(value2, value)
return test_2
a = test()
a()
如果一个函数的内部又定义了一个函数,那么这样就产生了嵌套作用域,其实嵌套作用域是一个相对概念。变量value存在于test函数所产生的局部作用域,变量value2存在于test_2函数所产生的局部作用域,value所在的作用域相对于value2来说就是一个嵌套作用域。
在函数test_2中可以访问test函数中的变量,但反过来就不行, 只允许向上访问。函数最后返回值是test_2,它是一个函数,赋值给a以后,a()就是在执行test_2函数
每个模块都是一个全局作用域,你也可以简单的理解为每个脚本就是一个全局作用域。在模块中创建的变量,这个模块里的任何地方都可以访问得到
示例1
value = 100
def test():
print(value)
test()
在局部作用域里,你可以使用这个变量,但你不能修改这个变量的值
示例2
value = 100
def test():
value = 99
print(value)
test()
print(value)
程序的输出结果是
99
100
道理很简单,当你执行value = 99时,其实是在局部作用域里创建了一个变量value,这个value和全局的那个value根本就不是同一个变量。
那么为什么,在示例1中,就可以访问到全局的那个value呢,这是因为在搜索变量时是按照顺序进行的
局部作用域 > 嵌套作用域 > 全局作用域 > 内置作用域
python会按照这个顺序搜索变量,示例1中现在局部作用域搜索,没有找到后去全局作用域,这时找到了。
如果想在函数里修改全局变量,必须使用global关键字
value = 100
def test():
global value
value = 99
print(value)
test()
print(value)
系统内固定模块里定义的变量,如预定义在builtin 模块内的变量
a = 3
b = 5
sum = a + b
print(sum)
lst = [1, 2, 3]
print(sum(lst))
上面这段代码执行会报错
TypeError: 'int' object is not callable
这是一个非常诡异的错误,很多初学者都曾经遇到过,看代码,看不出有任何问题,可就是报了一个奇怪的错误。问题出在代码的第三行 sum = a + b。 sum 是一个变量,它的值等于a + b,sum这个变量存在于全局作用域里,最后一行的代码试图通过内置函数sum求列表里的元素之和,内置函数的作用域是内置作用域,python在搜索变量时是按照
的顺序进行的,最后一行代码想要使用内置函数sum,但是由于全局作用域里已经有了一个sum变量,就不会去内置作用域里继续寻找了。全局作用域里sum的值 a+b = 8,是一个int类型数据,int类型数据当然不是callable的。
QQ交流群: 211426309