深浅copy以及赋值

对于字符串和数字而言,赋值、浅拷贝和深拷贝无意义,因为其永远指向同一个内存地址。

import copy

n1 =
#n1 = 'hahahaha'
#赋值
n2 = n1
#浅copy
n3 = copy.copy(n1)
#深copy
n4 = copy.deepcopy(n1)
print(id(n1),id(n2)) #打印内存地址
5787536 5787536
print(id(n1),id(i3))
5787536 5787536
print(id(n1),id(n4))
5787536 5787536

字典,列表,元组等进行赋值,深浅copy时,它们的内存地址变化是不一样的。

在赋值操作时,仅仅只是做了一个别名而已。因为字典的存储空间比字符串和数字要大很多,当你赋值给另一个变量的时候,按原来的方式copy一份独立的数据会浪费很多资源,

效率还会很低。

n1 = {'k1':,'k2':'koka','k3':['haha','xixi','hehe','houhou']}

n2 = n1
print(n2)
print(n1)
{'k3': ['haha', 'xixi', 'hehe', 'houhou'], 'k2': 'koka', 'k1': }
{'k3': ['haha', 'xixi', 'hehe', 'houhou'], 'k2': 'koka', 'k1': }
n1['k1']=
print(n2)
print(n1)
{'k3': ['haha', 'xixi', 'hehe', 'houhou'], 'k2': 'koka', 'k1': }
{'k3': ['haha', 'xixi', 'hehe', 'houhou'], 'k2': 'koka', 'k1': }
n1['k3'][]='ajx'
print(n2)
print(n1)
{'k3': ['ajx', 'xixi', 'hehe', 'houhou'], 'k2': 'koka', 'k1': }
{'k3': ['ajx', 'xixi', 'hehe', 'houhou'], 'k2': 'koka', 'k1': }

#从结果可以发现n1和n2的值同时改变,因为他们只是两个不同的别名而已。

在浅copy操作时,只是copy了字典下的第一层数据,对于更深层次的数据还是原来的。

n3 =copy.copy(n1)
print(n3)
print(n1)
{'k1': , 'k2': 'koka', 'k3': ['haha', 'xixi', 'hehe', 'houhou']}
{'k1': , 'k2': 'koka', 'k3': ['haha', 'xixi', 'hehe', 'houhou']}
n1['k2'] = 'dada'
print(n3)
print(n1)
{'k1': , 'k2': 'koka', 'k3': ['haha', 'xixi', 'hehe', 'houhou']}
{'k1': , 'k2': 'dada', 'k3': ['haha', 'xixi', 'hehe', 'houhou']}
n1['k3'][] = 'heihei'
print(n3)
print(n1)
{'k1': , 'k2': 'koka', 'k3': ['haha', 'xixi', 'heihei', 'houhou']}
{'k1': , 'k2': 'dada', 'k3': ['haha', 'xixi', 'heihei', 'houhou']}

#可以看出第一层的字符串数据改变了,而后面的列表还是同一个。

在深度copy操作时,在内存中将所有的数据重新创建一份(排除最后一层,即:python内部对字符串和数字的优化)

n4 = copy.deepcopy(n1)
print(n4)
print(n1)
{'k2': 'koka', 'k3': ['haha', 'xixi', 'hehe', 'houhou'], 'k1': 1024}
{'k2': 'koka', 'k3': ['haha', 'xixi', 'hehe', 'houhou'], 'k1': 1024}
n1['k1'] = 8192
n4['k2'] = 'akok'
print(n4)
print(n1)
{'k2': 'akok', 'k3': ['haha', 'xixi', 'hehe', 'houhou'], 'k1': 1024}
{'k2': 'koka', 'k3': ['haha', 'xixi', 'hehe', 'houhou'], 'k1': 8192}
n1['k3'][0] = "lolo"
n4['k3'][1] = "lala"
print(n4)
print(n1)
{'k2': 'akok', 'k3': ['lala', 'xixi', 'hehe', 'houhou'], 'k1': 1024}
{'k2': 'koka', 'k3': ['lolo', 'xixi', 'hehe', 'houhou'], 'k1': 8192}

#真正的完全copy一份数据。

数据结构扩展

Collection系列

1、计数器(counter)

Counter是对字典类型的补充,用于追踪值的出现次数。

ps:具备字典的所有功能 + 自己的功能

c1 = collections.Counter('aabc')
c2 = collections.Counter(('a','b','c','a'))
print(c1)
Counter({'a': , 'b': , 'c': })
print(c2)
Counter({'a': , 'b': , 'c': })
#类似于c1 + c2
c1.update(c2)
print(c1)
Counter({'a': , 'b': , 'c': })
c1.subtract('a')
print(c1)
Counter({'a': , 'b': , 'c': })
#列出前几位
print(c1.most_common())
[('a', ), ('b', )]
for i in c2.elements():
#elements返回元素迭代器
print(i)
b
a
a
c

2、有序字典(orderedDict )

有序字典跟字典使用没有区别,记录key的存储顺序

o1 = collections.OrderedDict()
o1['k1'] =
o1['k2'] =
o1['k3'] =
for i,k in o1.items():
print(i,k) k1
k2
k3 products = collections.OrderedDict()
products = {
:['nectarine',],
:['orange',],
:['raspberry',],
:['cherry',],
:['Apple',],
:['Banana',]
} format = '%-*s%*s%*s'
for i,k in products.items():
print(format %(,i,,k[],,k[]))
nectarine
orange
raspberry
cherry
Apple
Banana

3、默认字典(defaultdict)

defaultdict是对字典的类型的补充,他默认给字典的值设置了一个类型。

values = [, , ,,,,,,]
newvalues = collections.defaultdict(list) for i in values:
if i >= :
newvalues['k1'].append(i)
else:
newvalues['k2'].append(i)
print(newvalues)

4、可命名元组(namedtuple)

根据nametuple可以创建一个包含tuple所有功能以及其他功能的类型。

可命名元组:

1.创建类
2.使用类创建对象
3.使用对象
4.用于坐标
——————

普通元组:
1.直接使用类创建对象
2.使用对象

#old = tuple(1,2) <==> old = (1,2)
#创建一个扩展tuple的类,Mytuple

import collections
Mytuple = collections.namedtuple('Mytuple',['x','y'])
new = Mytuple(,)
print(new) Mytuple(x=1, y=2

5、双向队列(deque)

在需要按照元素增加的顺序来移除元素时非常有用,双向队列可以通过可迭代对象来创建。

q = collections.deque(range())
q.append()
q.appendleft()
print(q)
deque([, , , , , , ]) q.rotate()
print(q)
deque([, , , , , ]) q.rotate(-)
print(q)
deque([, , , , , ]) q.remove()
print(q)
deque([, , , , , ]) ret1 = q.pop()
print(ret1) ret2 = q.popleft()
print(ret2) q.extend([,,])
print(q)
deque([, , , , , , ]) q.extendleft([,,])
print(q)
deque([, , , , , , , , , ])

set 集合

set是一个无序且不重复的元素集合,主要用于成员查找。
>>> a = set([,,,])
>>> b = set([,,,,])
#去除重复项合并
a.update(b)
print(a)
{, , , , , , } #添加一个数
>>> a.add()
>>> print(a)
{, , , , , , , } #清空集合
>>>a.clear()
set() >>> c = a.copy()
>>> print(c)
{, , , , , , , } #并集
>>> result1 = a.union(b)
>>> result2 = a | b
>>> print(result1,result2)
{, , , , , , , } {, , , , , , , } #交集
>>> result = a.intersection(b)
>>> print(result)
{, , , , }
>>> result = a & b
>>> print(result)
{, , , , } #子集
>>> result = c.issubset(a)
>>> print(result)
True #父集
>>> result = a.issuperset(c)
>>> print(result)
True #取差集 -
>>> result1 = a.difference(b)
>>> result2 = a - b
>>> print(result1,result2)
{, , } {, , } #异或差集 &
result1 = a ^ b
result2 = a.symmetric_difference(b)
print(result1,result2)
{, , } {, , } #删除
# remove(If the element is not a member, raise a KeyError.)
# discard (If the element is not a member, do nothing.)
#pop (Remove and return an arbitrary set element.Raises KeyError if the set is empty.)
a.remove()
print(a)
{, , , , , , } a.discard()
print(a)
{, , , , , } a.pop() print(a)
{, , , , }

集合练习:

找出下面字典中不同的键,同样的更新,现在没有的删除,现在有的更新

old_dict = {
"#1":{ 'hostname':'c1', 'cpu_count': 2, 'mem_capicity': 80 },
"#2":{ 'hostname':'c1', 'cpu_count': 2, 'mem_capicity': 80 },
"#3":{ 'hostname':'c1', 'cpu_count': 2, 'mem_capicity': 80 }
}
new_dict = {
"#1":{ 'hostname':'c1', 'cpu_count': 2, 'mem_capicity': 800 },
"#3":{ 'hostname':'c1', 'cpu_count': 2, 'mem_capicity': 80 },
"#4":{ 'hostname':'c2', 'cpu_count': 2, 'mem_capicity': 80 }
}
old_set =set(old_dict.keys())
new_set = set(new_dict.keys())
update_set = old_set.intersection(new_set)
del_list = list(old_set.difference(update_set))
add_list = list(new_set.difference(update_set))
print(list(update_set),add_list,del_list)

堆(heap)

它是一种优先队列。它能够以任意顺序增加对象,并且能在任何时间(可能在增加对象的同时)找到(也可能是移除)最小的元素,它比列表的min方法更有效率。
相关函数:
heappush(x)          将X入堆
heappop(heap)        将堆中最小的元素弹出
heapify(heap)        将堆中属性强制应用到任意一个列表,如果没有使用haeppush创建堆,可以使用heapif(heap)
heapreplace(heap,x)  将堆中最小元素弹出,同时将x入堆
nlargest(n,iter)   返回iter中第n大的元素
nsmallest(n,iter)    返回iter中第n小的元素

from heapq import *
from random import shuffle seq = [11,22,33,44,55]
shuffle(seq)
heap = []
for i in seq:
heappush(heap,i)
print(heap)
[11, 22, 44, 55, 33]
heappush(heap,10)
print(heap)
[10, 22, 11, 55, 33, 44]

元素的顺序并不像看起来那么随意,算法:位于i位置上的元素总比1//2位置处的元素大(反过来说就是i位置的元素总比2*以及2*i+1位置处的元素小)

print(heappop(heap))
10
print(heappop(heap))
11
print(heappop(heap))
22

一般来说都是在索引0处的元素,并且会确保剩余元素中最小的那个占据这个位置

li = [1,2,5,4,67,27,2]
heapify(li)
print(li) heapreplace(li,0.5)
print(li)

python学习笔记三 深浅copy,扩展数据类型(基础篇)的更多相关文章

  1. python学习笔记六 初识面向对象上(基础篇)

    python面向对象   面向对象编程(Object-Oriented Programming )介绍   对于编程语言的初学者来讲,OOP不是一个很容易理解的编程方式,虽然大家都知道OOP的三大特性 ...

  2. python学习笔记(4)-基本数据类型-数字类型及操作

    大学mooc 北京理工大学 python语言程序设计课程学习笔记 一.整数类型 可正可负,没有取值范围的限制(这个与c不同,c要考虑数据类型的存储空间).如pow(x,y),计算x的y次方,pow(2 ...

  3. Python 学习笔记三

    笔记三:函数 笔记二已取消置顶链接地址:http://www.cnblogs.com/dzzy/p/5289186.html 函数的作用: 給代码段命名,就像变量給数字命名一样 可以接收参数,像arg ...

  4. Python学习笔记三:数据类型

    数据类型 整数int 32位机器,-2**31~2**31-1,即-2147483648~2147483647(4亿多) 64位机器,-2**63~2**63-1,非常大了. 长整型long 没有位数 ...

  5. webdriver(python) 学习笔记三

    知识点:简单的对象定位 对象的定位应该是自动化测试的核心,要想操作一个对象,首先应该识别这个对象.一个对象就是一个人一样,他会有各种的特征(属性),如比我们可以通过一个人的身份证号,姓名,或者他住在哪 ...

  6. python学习笔记(三)、字典

    字典是一种映射类型的数据类型.辣么什么是映射呢?如果看过<数据结构与算法>这一本书的小伙伴应该有印象(我也只是大学学习过,嘻嘻). 映射:就是将两个集合一 一对应起来,通过集合a的值,集合 ...

  7. python学习笔记:深浅拷贝的使用和原理

    在理解深浅拷贝之前,我们先熟悉下变量对象和数据类型 1.变量和对象 变量-引用-对象(可变对象,不可变对象) 在python中一切都是对象,比如[1,2],'hello world',123,{'k1 ...

  8. python学习笔记2(pycharm、数据类型)

    Pycharm 的使用 IDE(Integrated  Development  Environ ment) :集成开发环境 Vim  :经典的linux下的文本编辑器(菜鸟和大神喜欢使用) Emac ...

  9. Python学习笔记三

    一. 为什么要使用函数? 函数可以方便阅读代码. 函数可以减少重复代码. 函数可以减少管理操作,减少修改操作. 二. 函数分类: 内置函数:len()   sum()   max()   min() ...

随机推荐

  1. 使用Eclipse构建Maven项目 (转)

    Maven这个个项目管理和构建自动化工具,越来越多的开发人员使用它来管理项目中的jar包.本文仅对Eclipse中如何安装.配置和使用Maven进行了介绍.完全step by step. 如果觉得本文 ...

  2. javascript语法详解

    javascript语法:运算符 条件语句if...else...  条件语句switch  循环语句for  循环语句while   跳转语句 js运算符 1.算数运算符:+ - * % / ++ ...

  3. linux第11天 共享内存和信号量

    今天主要学习了共享内存和信号量 在此之前,有个管道问题 ls | grep a 整句话的意思是将ls输出到管道的写端,而流通到另一端的读端,grep a则是从管道的读端读取相关数据,再做筛选 共享内存 ...

  4. bzoj2743 [HEOI2012]采花

    做法是每个询问先算出询问区间中花的种类减去区间中只有一朵花的花的种类,这两个子问题都不算难,具体看代码吧.询问可以离线处理,用树状数组维护,复杂度O(nlogn). 不知道是想的复杂了还是打的太low ...

  5. shell 命令

  6. 1.js基础

    1.如何在html文档中使用js 1)使用<script></script>将JS语法嵌入到html中,可以使用多个,每个之间都是有关联的 2)href="javas ...

  7. Sql Server Analysis Service 处理时找到重复的属性键、找不到属性键错误(转载)

    这是两个非常常见的SSAS处理异常,网上也能找到很多文章讲解决办法,但很少见关于异常原因的分析,先来看看第一个" OLAP 存储引擎中存在错误: 处理时找到重复的属性键",一个维度 ...

  8. 一小时学会Markdown写作

    写作也是创作一件产品.以易懂.简洁.凝练的方式表达观点.阐述见解和知识,发挥影响力. 为什么要使用 Markdown 博文迁移的排版兼容.当在多个博客之间,或者在线博客与本地笔记软件之间迁移的时候,排 ...

  9. mysql datetime设置now()无效,直接用程序设置默认值比较好

    mysql datetime设置now()无效的,没有此用法,datetime类型不能设置函数式默认值,只能通过触发器等来搞.想设置默认值,只能使用timestamp类型,然后默认值设置为:CURRE ...

  10. 点评js异步加载的4种方式

    主要介绍了点评js异步加载的4种方式,帮助大家更全面的了解js异步加载方式,感兴趣的小伙伴们可以参考一下 js异步加载的4种方式,点评开始. <!DOCTYPE html> <htm ...