这篇笔记只是个人拙见,可能有不对的地方,还请海涵
Python传参机制
Python 中一切皆为对象,数字是对象,列表是对象,函数也是对象,任何东西都是对象。而变量只是对象的一个引用,对象的操作都是通过引用来完成的
个人认为,python函数内重新赋值时,不会改变函数外的值,但在函数内修改成员变量的值时,会改变函数外的值
python内存分配机制
这个机制让我想起了Java的字符串分配内存的情形
1 2 3 4 5 6 7 8 9 10 11 12 13
| public class Test{ public static void main(String[] args) { String s1="hello"; String s2="hello"; String s3=new String("hello"); System.out.println(s1==s2); System.out.println(s1==s3); System.out.println(s1.equals(s3)); int num1=1; int num2=1; System.out.println(num1==num2); } }
|
放一段代码以做对照
对于不可变对象
关于不可变对象(数字、字符或元组),来看一个例子
1 2 3 4 5 6 7 8
| a=1 b=1 c=1 print(id(a),id(b),id(c)) b=2 c+=1 print(id(a),id(b),id(c))
|
可以看出,值相同,就是指向一样的内存地址
对于可变对象
关于可变对象(字典、列表),来看一个例子
1 2 3 4 5 6 7 8
| a=[1,2] b=[1,2] c=[1,2] print(id(a),id(b),id(c)) b.append(3) c.append(3) print(id(a),id(b),id(c))
|
修改其中的值后,会指向新的对象
对于赋值
赋值会为新的值开辟新的空间
1 2 3 4 5 6 7 8 9 10
| def fun(x): print('赋值前x的地址是'+str(id(x))) x=2 print('赋值后x的地址是'+str(id(x)))
a=1 print('赋值前a的地址是'+str(id(a))) fun(a) print(a)
|
即使是实参是列表也是一样
1 2 3 4 5 6 7 8 9 10
| def fun(x): print('赋值前x的地址是'+str(id(x))) x=2 print('赋值后x的地址是'+str(id(x)))
a=[1] print('赋值前a的地址是'+str(id(a))) fun(a) print(a)
|
对于修改值
修改值会影响函数外面的值
1 2 3 4 5 6 7 8 9 10 11 12
| def func(x): x['a'] = 1 x['b'] = 2 print(x) x = {'a': 3, 'b': 4} print(x)
t = {} func(t) print(t)
|
看一个类的例子
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| class Test: def __init__(self) -> None: x=1 def __call__(self): print(self.x)
def fun(t:Test): t.x=2 t()
a=Test() fun(a)
|
也是一样的
修改全局变量
顺便说一下怎么修改全局变量
直接修改是修改不了的
1 2 3 4 5 6
| def fun(): a=2
a=1 fun() print(a)
|
事实上,修改不了的原因应该在于函数内部是无法直接访问全局变量的
1 2 3 4 5 6
| a=1 def fun(): print(a) a=2
fun()
|
想要修改的话,可以使用global
这个关键字
1 2 3 4 5 6 7
| def fun(): global a=2
a=1 fun() print(a)
|
像这样就修改成功了
1 2 3 4 5 6 7
| def fun(): global a a=2
a=1 fun() print(a)
|