首页 > 解决方案 > Python 中的可变性以及它为什么会发生?

问题描述

所以我试着让我的大脑中的可变性更好一些,我看到很多有经验的人有时都在挣扎。

我在这里做了这个小测试代码:

x = 1
def test():
    x = 2
test()
print(x) #1


x = 1
def test():
    global x
    x = 2
test()
print(x) #2


x = [1]
def test():
    x = [2]
test()
print(x) #[1]


x = [1]
def test():
    global x
    x = [2]
test()
print(x) # [2]


x = [1]
def test():
    x[0] = 2
test()
print(x) #[2]

一切对我来说都很清楚,除了最后一个和倒数第二个之间的区别可能是什么。这到底是什么规则。我注意到可以更改对象的值,但不能更改对象类型本身,还是我理解错了?

标签: pythonlistimmutability

解决方案


# case 1
x = 1
def test():
    x = 2
test()
print(x) #1

# case 2
x = 1
def test():
    global x
    x = 2
test()
print(x) #2

x在情况 1 中,内部变量test是局部范围的,因此更改其值不会更改外部声明的 x 的值,test因此不会改变x外部声明的 x 值test

在情况 2 中,变量xinsidetest是全局范围的,因此更改其值确实会更改外部声明的 x 的值,因此会在外部test发生变异。xtest


# case 3
x = [1]
def test():
    global x
    x = [2]
test()
print(x) # [2]

# case 4
x = [1]
def test():
    x[0] = 2
test()
print(x) #[2]

在情况 3 中,x内部列表test的全局范围为 保存对外部列表的引用test,但是当您将新列表分配给 时x,会创建对此列表的新引用,[2]并且改变这个新列表不会改变列表中的值对外宣布test

在第 4 种情况下,方法x内的列表test包含对在函数外部声明的同一列表实例的引用test,当您调用时,x[0]您不会更改对列表的引用,而是将值分配给2同一index 0列表内,这改变外部列表。


推荐阅读