目录
·copy()浅复制
·deepcopy()深复制
·把一个列表变量赋值给另外一个变量
写在最前:
Python采用的是基于值的自动内存管理模式,变量并不直接赋值,而是存储值的引用或内存地址。
这也是为什么Python中变量可以随时改变类型的重要原因。
Python列表中的值也是值的引用。
x = [1,1,1];
a = id(x[0]);
b = id(x[1]);
print('id of x[0] :',a);
print('id of x[1] :',b);
输出结果
·copy()
列表对象的copy()方法返回列表的浅复制。
那到底什么是浅复制?通俗的讲就是生成一个新的列表,并把原列表中所有元素的引用都复制到新列表中。注意是复制了引用!!
那么如果原列表中有可变的数据类型,修改以后将会影响新列表。
x = [1,2,[4,5]];
'''
浅复制,如果列表中只包含整数,实数,复数等基本类型或元组,
字符串这种不可变的数据类型,一般没有问题。
但是如果原列表中包含可变的数据类型时,由于浅复制只是把字列表的引用复制到新列表中,
于是修改任何一个都会影响另外一个
'''
y = x.copy();
print('x : ',x);
print('y : ',y);
x[0] = 6;
print('x : ',x);
print('y : ',y);
y[2].append(6);
print('x : ',x);
print('y : ',y);
输出结果
·deepcopy()深复制
如果想避免上面代码演示的问题,可以使用标准库copy中的deepcopy()函数实现深复制。所谓深复制,就是对原列表的元素进行递归,把所有的值都复制到新列表中,对嵌套的字列表不再是复制引用。那么新列表与原列表就相互独立了。
import copy
x = [1,2,[4,5]];
y = copy.deepcopy(x);
print('x :',x);
print('y :',y);
x[2].append(6);
y.append(8);
print('x :',x);
print('y :',y);
输出结果
·把一个列表变量赋值给另外一个变量
把一个列表变量赋值给另外一个变量,这样两个变量指向同一个列表对象,对其中一个做的任何修改都会立刻在另外一个变量得到体现。
x = [1,2,3,[4,5]];
y = x;
print('x :',x);
print('y :',y);
x.append(4);
x[3].append(89);
print('y :',y);
输出结果
从这个例子可以看到,我们只是对x做出修改,但是y也受到了改变。
为了避免这种情况我们可以采用切片复制。
x = [1,2,3,[4,5]];
y = x[:];
print('x :',x);
print('y :',y);
x.append(4);
x[3].append(89);
print('y :',y);
很明显,切片复制和copy()复制原理一样,所以如果想要复制一个列表,使得新列表与就列表完全独立,使用deepcopy()。