python中的对象拷贝示例 python引用传递

何谓引用传递,我们来看一个C++交换两个数的函数:

代码如下:

void swap(int &a, int &b)
{
    int temp;
    temp = a;
    a = b;
    b = temp;
}

这个例子就是一个引用传递的例子!目的是说明一下概念:引用传递的意思就是说你传递的是对象的引用,对这个引用的修改也会导致原有对象的改变。学过C/C++的朋友们都知道,在交换2个数的时候,如果自己实现一个swap函数,需要传递其引用或者指针。

Python直接使用引用传递,多方便啊,你还要吐槽什么?你又想过我不想改变原对象的情况吗?如果有,那么看这里!

假设我现在有一个list,叫做l1,我现在需要一份l1的拷贝,如果我直接使用诸如l2 = l1的方式,然后我对l2进行一系列的修改,会等价于我对l1直接做修改,这可不是我想要的!如:

代码如下:

l1 = [1, 2]
l2 = l1
l2.append(3)
print l1
print l2
# l1 = [1, 2, 3], l2 = [1, 2, 3]

这就是Python引用传递造成的,也就是说l1和l2属于同一list对象,那么如何才能得到一份不同的对象呢?这不是so easy嘛,用切片撒,比如:


代码如下:

l1 = [1, 2]
l2 = l1[:]
l2.append(3)
# l1 = [1, 2], l2 = [1, 2, 3]

是的,目的达到了,别介,你确定这样一定行?让我们看看一个更复杂的情况:

代码如下:

l1 = [[1, 2], 3]
l2 = l1[:]
l2.append(4)
# l1 = [[1, 2], 3], l2 = [[1, 2], 3, 4]
l2[0].append(5)
# l1 = [[1, 2, 5], 3], l2 = [[1, 2, 5], 3, 4]

啊哈,貌似出问题了哈,这个可不是我们需要的!怎么办呢?好了,进入今天的正题,Python中的copy模块!


代码如下:

import copy

如果你希望复制一个容器对象,以及它里面的所有元素(包含元素的子元素),使用copy.deepcopy,这个方法会消耗一些时间和空间,不过,如果你需要完全复制,这是唯一的方法。上面我们提到的切片的方式,等价于copy模块中的copy函数。

上面拷贝的操作变得so easy了:

代码如下:

l1 = [[1, 2], 3]
l2 = copy.copy(l1)
l3 = copy.deepcopy(l1)
l2.append(4)
l2[0].append(5)
l3[0].append(6)
# l1 = [[1, 2, 5], 3], l2 = [[1, 2, 5], 3, 4], l3 = [[1, 2, 6], 3]

相关说明:


代码如下:

copy(x)
    Shallow copy operation on arbitrary Python objects.
    See the module's __doc__ string for more info.
deepcopy(x, memo=None, _nil=[])
    Deep copy operation on arbitrary Python objects.
    See the module's __doc__ string for more info.

(0)

相关推荐

  • python传递参数方式小结

    本文实例总结了python传递参数方式.分享给大家供大家参考.具体分析如下: 当形参如*arg时表示传入数组,当形参如**args时表示传入字典. def myprint(*commends,**map): for comm in commends: print comm for key in map.keys(): print key,map[key] myprint("hello","word",username="tian",name=&q

  • 跟老齐学Python之总结参数的传递

    就前面所讲,函数的基本内容已经完毕.但是,函数还有很多值得不断玩味的细节.这里进行阐述. 参数的传递 python中函数的参数通过赋值的方式来传递引用对象.下面总结通过总结常见的函数参数定义方式,来理解参数传递的流程. def foo(p1,p2,p3,...) 这种方式最常见了,列出有限个数的参数,并且彼此之间用逗号隔开.在调用函数的时候,按照顺序以此对参数进行赋值,特备注意的是,参数的名字不重要,重要的是位置.而且,必须数量一致,一一对应.第一个对象(可能是数值.字符串等等)对应第一个参数,

  • Python函数可变参数定义及其参数传递方式实例详解

    本文实例讲述了Python函数可变参数定义及其参数传递方式.分享给大家供大家参考.具体分析如下: python中 函数不定参数的定义形式如下: 1.func(*args) 传入的参数为以元组形式存在args中,如: def func(*args): print args >>> func(1,2,3) (1, 2, 3) >>> func(*[1,2,3]) #这个方式可以直接将一个列表的所有元素当作不定参数 传入(1, 2, 3) 2.func( **kwargs)

  • python进阶教程之函数参数的多种传递方法

    我们已经接触过函数(function)的参数(arguments)传递.当时我们根据位置,传递对应的参数.我们将接触更多的参数传递方式. 回忆一下位置传递: 复制代码 代码如下: def f(a,b,c):     return a+b+c print(f(1,2,3)) 在调用f时,1,2,3根据位置分别传递给了a,b,c. 关键字传递 有些情况下,用位置传递会感觉比较死板.关键字(keyword)传递是根据每个参数的名字传递参数.关键字并不用遵守位置的对应关系.依然沿用上面f的定义,更改调用

  • 浅谈python抛出异常、自定义异常, 传递异常

    一. 抛出异常 Python用异常对象(exception object)表示异常情况,遇到错误后,会引发异常.如果异常对象并未被处理或捕捉,程序就会用所谓的回溯(Traceback,一种错误信息)终止执行. raise 语句 Python中的raise 关键字用于引发一个异常,基本上和C#和Java中的throw关键字相同,如下所示: import traceback def throw_error(): raise Exception("抛出一个异常")#异常被抛出,print函数

  • python下函数参数的传递(参数带星号的说明)

    函数参数的使用又有俩个方面值得注意:1.函数参数是如何定义的 2.在调用函数的过程中参数是如何被解析 先看第一个问题,在python中函数参数的定义主要有四种方式: 1.F(arg1,arg2,...) 这 是最常见的定义方式,一个函数可以定义任意个参数,每个参数间用逗号分割,用这种方式定义的函数在调用的的时候也必须在函数名后的小括号里提供个数相等的 值(实际参数),而且顺序必须相同,也就是说在这种调用方式中,形参和实参的个数必须一致,而且必须一一对应,也就是说第一个形参对应这第一个实参.例 如

  • python和shell变量互相传递的几种方法

    python -> shell: 1.环境变量 复制代码 代码如下: import os  var=123或var='123'os.environ['var']=str(var)  #environ的键值必须是字符串   os.system('echo $var') 复制代码 代码如下: import os  var=123或var='123'os.environ['var']=str(var)  #environ的键值必须是字符串  os.system('echo $var') 2.字符串连接

  • Python def函数的定义、使用及参数传递实现代码

    Python编程中对于某些需要重复调用的程序,可以使用函数进行定义,基本形式为: def 函数名(参数1, 参数2, --, 参数N): 执行语句函数名为调用的表示名,参数则是传入的参数,可以更具需要定义,也可以没有. # 例1:简单的函数使用 # coding=gb2312 # 定义函数 def hello(): print 'hello python!' # 调用函数 hello() >>> hello python! 函数可以带参数和返回值,参数将按从左到右的匹配,参数可设置默认值

  • 解决Python传递中文参数的问题

    今天有个需要需要传递中文参数给URL 但是在GBK环境下的脚本传递GBK的参数老是给我报UNICODE的解码错误.烦的很. 所以我们果断选择用urlencode来处理中文, 由于国内外网站编码不同,国内是GBK的,国外是UTF8的. >>> import sys >>> sys.stdin.encoding 'GBK' 表示我们的环境是GBK的 >>> import urllib >>> urllib.quote('编码坑爹') '%

  • 利用Python命令行传递实例化对象的方法

    一.前言 在开发过程中,遇到了这样一个情况:我们需要在脚本中通过 suprocess.call 方法来启动另外一个脚本(脚本 B),当然啦,还得传递一些参数.在这些参数中,有一个需要传递的是一个实例化后的对象.我们知道,通过命令行的方式传递参数是基于字符格式的,也就是说脚本 B 只能接收到字符串格式的参数,那么如何接收启动脚本传递过来的实例化后的对象呢? 今天就来聊聊我使用的两种笨方法:使用 eval 以及使用 pickle 和 base64 模块. 方法一:使用 eval 其实在代码中使用 e

随机推荐