Python中实现变量赋值传递时的引用和拷贝方法


Posted in Python onApril 29, 2018

iamlaosong文

曾经看到这样一个问题,一个字典中的元素是列表,将这个列表元素赋值给一个变量,然后修改这个列表中元素的值,结果发现,字典中那个列表也同样修改了。

那个问题如下:

dict = {'a':[1,2,3,4,5],'b':2} 
x = dict['a'] 
for i in range(5): 
  x[i] = 0 
print(dict['a'])

程序运行结果如下:

[0, 0, 0, 0, 0]

这儿涉及到Python赋值到底是引用还是拷贝一份的问题,即赋值时是传值还是传址。上面问题是将“a”的值赋给了x出现了上述情况,如果是将“b”的值赋给了x,当我们修改x的值时,字典dict的值并不受影响。

>>> dict = {'a':[1,2,3,4,5],'b':2} 
>>> x = dict['b'] 
>>> x 
2 
>>> x=x+3 
>>> x 
5 
>>> dict 
{'a': [1, 2, 3, 4, 5], 'b': 2} 
>>>

那么问题来了,变量赋值传递时什么情况下是传值(拷贝),什么情况下是传址(引用)呢?

1、直接拷贝

当我们不知道是引用还是拷贝的情况下,可以显式的拷贝。比如字典对象本身都具有拷贝的方法:

x=dict.copy()

没有拷贝方法的对象,也是可以拷贝的。这儿我们引入一个深拷贝的概念,深拷贝——即python的copy模块提供的一个deepcopy方法。深拷贝会完全复制原变量相关的所有数据,在内存中生成一套完全一样的内容,在这个过程中我们对这两个变量中的一个进行任意修改都不会影响其他变量。还是上面的代码,如果改成如下:

import copy 
dict = {'a':[1,2,3,4,5],'b':2} 
x = copy.deepcopy(dict['a']) 
for i in range(5): 
  x[i] = 0 
print(dict['a'])

运行结果dict值不受影响。

除了深拷贝,copy模块还提供一个copy方法,称其为浅拷贝,对于简单的对象,深浅拷贝都是一样的,上面的词典对象的copy方法就是浅拷贝。

>>> dict
{'a': [8, 2, 3, 4, 5], 'b': 4}
>>> dd=copy.copy(dict)
>>> dd
{'a': [8, 2, 3, 4, 5], 'b': 4}
>>> dd['a'][0]=7
>>> dd
{'a': [7, 2, 3, 4, 5], 'b': 4}
>>> dict
{'a': [7, 2, 3, 4, 5], 'b': 4}
>>> ee=dict.copy()
>>> ee
{'a': [7, 2, 3, 4, 5], 'b': 4}
>>> ee['a'][0]=9
>>> ee
{'a': [9, 2, 3, 4, 5], 'b': 4}
>>> dict
{'a': [9, 2, 3, 4, 5], 'b': 4}
>>> ee['b']=5
>>> ee
{'a': [9, 2, 3, 4, 5], 'b': 5}
>>> dict
{'a': [9, 2, 3, 4, 5], 'b': 4}
>>>

浅拷贝时改变第一层次相互不受影响(上例中词典b值的修改),第二层次(上例中词典a的列表值修改)就相互影响了,改一个,其他跟着变。看看id吧:

>>> id(dict) 
20109472 
>>> id(dd) 
20244496 
>>> id(ee) 
20495072 
>>> id(dd['a']) 
20272112 
>>> id(ee['a']) 
20272112 
>>> id(dict['a']) 
20272112 
>>>

可见词典各个拷贝的id是不同的,但词典a值的id是相同的。如果我们需要真正意义的拷贝,就用深拷贝吧。

2、传递规则

Python赋值过程中不明确区分拷贝和引用,一般对静态变量的传递为拷贝,对动态变量的传递为引用。(注,对静态变量首次传递时也是引用,当需要修改静态变量时,因为静态变量不能改变,所以需要生成一个新的空间存储数据)。

字符串,数值,元组均为静态变量

列表,字典为动态变量。

变量有时比较复杂,存在组合现象,比如字典中包含列表,列表中包含字典,但赋值时,总是属于某个类型。如果实在不清楚状况,可以试验一下,用id()这个函数看看,如果是引用,两个变量指向的地址是相同的。例如:

>>> a=6 
>>> id(a) 
10413476 
>>> b=a 
>>> id(b) 
10413476 
>>> b=8 
>>> id(b) 
10413452 
>>>

修改变量b之前,a和b指向的地址是相同的,修改b后,地址就变了。

以上这篇Python中实现变量赋值传递时的引用和拷贝方法就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
进一步了解Python中的XML 工具
Apr 13 Python
Python对象转JSON字符串的方法
Apr 27 Python
Python实现的桶排序算法示例
Nov 29 Python
浅谈tensorflow1.0 池化层(pooling)和全连接层(dense)
Apr 27 Python
Python爬虫获取图片并下载保存至本地的实例
Jun 01 Python
Python3网络爬虫中的requests高级用法详解
Jun 18 Python
python 矢量数据转栅格数据代码实例
Sep 30 Python
Windows下Pycharm远程连接虚拟机中Centos下的Python环境(图文教程详解)
Mar 19 Python
详解用selenium来下载小姐姐图片并保存
Jan 26 Python
python绘制高斯曲线
Feb 19 Python
Django使用echarts进行可视化展示的实践
Jun 10 Python
简单介绍Python的第三方库yaml
Jun 18 Python
分享一下Python数据分析常用的8款工具
Apr 29 #Python
Python随机函数random()使用方法小结
Apr 29 #Python
Python中py文件引用另一个py文件变量的方法
Apr 29 #Python
python实现类之间的方法互相调用
Apr 29 #Python
Python装饰器原理与简单用法实例分析
Apr 29 #Python
Python2.7 实现引入自己写的类方法
Apr 29 #Python
Python 实现引用其他.py文件中的类和类的方法
Apr 29 #Python
You might like
统一接口:为FireFox添加IE的方法和属性的js代码
2007/03/25 Javascript
基于jquery.Jcrop的头像编辑器
2010/03/01 Javascript
基于jQuery的仿flash的广告轮播代码
2010/11/04 Javascript
PHP 与 js的通信(via ajax,json)
2010/11/16 Javascript
多个js与css文件的合并方法详细说明
2012/12/26 Javascript
为JS扩展Array.prototype.indexOf引发的问题探讨及解决
2013/04/24 Javascript
Textarea根据内容自适应高度
2013/10/28 Javascript
jquery使用jxl插件导出excel示例
2014/04/14 Javascript
jquery UI Datepicker时间控件的使用方法(加强版)
2015/11/07 Javascript
纯js实现手风琴效果
2020/04/17 Javascript
省市联动效果的简单实现代码(推荐)
2016/06/06 Javascript
文本框只能输入数字的js代码(含小数点)
2016/07/10 Javascript
JavaScript toUpperCase()方法使用详解
2016/08/26 Javascript
实现一个完整的Node.js RESTful API的示例
2017/09/29 Javascript
vue移动端城市三级联动组件使用详解
2019/07/26 Javascript
layer.open组件获取弹出层页面变量、函数的实例
2019/09/25 Javascript
初步介绍Python中的pydoc模块和distutils模块
2015/04/13 Python
Python实用日期时间处理方法汇总
2015/05/09 Python
Python读取Excel的方法实例分析
2015/07/11 Python
将Python代码嵌入C++程序进行编写的实例
2015/07/31 Python
python3.0 模拟用户登录,三次错误锁定的实例
2017/11/02 Python
Python实现Linux监控的方法
2019/05/16 Python
使用Python生成200个激活码的实现方法
2019/11/22 Python
Python文本处理简单易懂方法解析
2019/12/19 Python
django实现将后台model对象转换成json对象并传递给前端jquery
2020/03/16 Python
德国街头和运动文化高品质商店:BSTN Store
2017/08/26 全球购物
中专毕业生自荐信
2013/11/16 职场文书
求职毕业生自荐书
2014/02/08 职场文书
高中学生评语大全
2014/04/25 职场文书
我的小天地教学反思
2014/04/30 职场文书
企业年度评优方案
2014/06/02 职场文书
2014年行政助理工作总结
2014/11/19 职场文书
2016春节家属慰问信
2015/03/25 职场文书
七一表彰大会简报
2015/07/20 职场文书
《植树问题》教学反思
2016/03/03 职场文书
Elasticsearch 配置详解
2022/04/19 Java/Android