字典和列表的删除问题, 深浅拷贝

一. 基础数据类型

1. str. join()

  str. join(元组、列表、字典、字符串)可以把这些都转变成字符串.

a = 'hello'.join('123')
b = '123'.join('hello')
print(a)  #1hello2hello3
print(b)  #h123e123l123l123o


li = ['hello','world','code']
str1 = '*'.join(li)
print(str1)  #hello*world*code

tu = ('welcome','you','are')
str2 = '@'.join(tu)
print(str2)  #welcome@you@are

dic = {'name':'王力宏','job':'singer','age':'42'}
str3 = '_'.join(dic)
print(str3)  #name_job_age

2. list删除

  列表循环时不能不可以进行删除操作.因为删除一个元素后,剩下的索引会发生改变.一开始这个指针指向第0 个. 然后获取到第0个元素. 紧接着删除第0个. 这个时候. 原来是第一个的元素会自动的变成第0个. 然后指针向后移动一次, 指向1元素.  这时原来的1已经变成了0, 也就不会被删除了.  

li = ['hello','world','code']
for c in li:
    li.remove(c)
print(li)  #['world']
li = ['hello','world','code']
for c in li:
    li.pop()
print(li)  #['hello']
li = ['hello','world','code']
for c in range(len(li)):
    del li[c]
print(li)  #报错

  用pop可以删除:

li = ['hello','world','code']
for n in range(0,len(li)):
    li.pop()
print(li)  #[]

 

  所以想要删除列表中的元素,要另建一个新列表来存储原列表的内容.对新列表进行循环,来删除原列表的元素.

li = ['hello','world','code']
li1 = []
for c in li:
    li1.append(c)
for el in li1:
    li.remove(el)
print(li)  #[]
 

3. 字典增加删除

  字典不能再循环的时候更改大小,所以循环的时候字典不可以增加删除.

dic1 = {"a":"123", "b":"456"}
for k in dic1:
    dic1.setdefault("c", "123")  
print(dic1)  #报错 RuntimeError: dictionary changed size during iteration

dic2 = {"a":"321", "b":"654"}
for k in dic2:
    dic2.pop(k)
print(dic2)  #报错 #RuntimeError: dictionary changed size during iteration

  对字典循环删除,要先建一个新列表来存储字典的key值,再对列表循环,然后删除字典元素.

dic1 = {"a":"123", "b":"456"}
li = []
for k in dic1:
    li.append(k)
for el in li:
    dic1.pop(el)
print(dic1)  #{}

dict中的fromkey(),可以帮我们通过list来创建一个dict

dic = dict.fromkeys("王健林", "思聪" ) # 返回给你一个新字典
print(dic)  #{'王': '思聪', '健': '思聪', '林': '思聪'}

4. 类型转换

元组 => 列表        list(tuple)

列表 => 元组        tuple(list)

list => str     str.join(list)

str => list     str.split()

三. 深浅拷贝

  将一个列表赋值给lst1, 再将lst1赋值给lst2, lst1和late2的内存地址一样,共同指向同一个列表. 对lst2进行增加操作,lst1也会改变

lst1 = ["金毛狮王", "紫衫龙王", "白眉鹰王", "青翼蝠王"]
lst2 = lst1 # 列表, 进行赋值操作. 实际上是引用内存地址的赋值. 内存中此时只有一个列表. 两个变量指向一个列表

lst2.append("杨左使")  # 对其中的一个进行操作. 两个都跟着变
print(lst2)  #['金毛狮王', '紫衫龙王', '白眉鹰王', '青翼蝠王', '杨左使']
print(lst1)  #['金毛狮王', '紫衫龙王', '白眉鹰王', '青翼蝠王', '杨左使']

  字典也是一样

dic1 = {1:"金毛狮王", 2:"紫衫龙王",3: "白眉鹰王", 4:"青翼蝠王"}
dic2 = dic1 #  两个变量的内存一样,指向同一个列表. 

dic2.setdefault(5,"杨左使")  # 对其中的一个进行操作. 两个都跟着变
print(dic2)  #{1: '金毛狮王', 2: '紫衫龙王', 3: '白眉鹰王', 4: '青翼蝠王', 5: '杨左使'}
print(dic1)  #{1: '金毛狮王', 2: '紫衫龙王', 3: '白眉鹰王', 4: '青翼蝠王', 5: '杨左使'}

  对于list, set, dict来说, 直接赋值. 其实是把内存地址交给变量. 并不是复制一份内容. 所以. lst1(dic1)的内存指向和lst2(dic2)是一样的. lst1(dic1)改变了了, lst2(dic2)也发生了改变.

1. 浅拷贝

  浅拷贝, 只会拷贝第一层. 第二层的内容不会拷贝. 所以被称为浅拷贝.用copy()来进行拷贝.

lst1 = ["赵本山", "刘能", "赵四"]
lst2 = lst1.copy()  # lst2 和lst1 不是一个对象了
# lst2 = lst1[:]  # 也可以用切片,切片会产生新的对象
lst1.append("谢大脚")
print(lst1, lst2)  #['赵本山', '刘能', '赵四', '谢大脚'] ['赵本山', '刘能', '赵四']

2.深拷贝

  浅拷贝只能拷贝第一层,遇到有第二层的列表,无法对第二层进行拷贝.对拷贝后的变量lst1第二层更改,lst1也会改变.

lst1 = ["超人", "七龙珠", "葫芦娃", "山中小猎人", ["金城武", "王力宏", "渣渣辉"]]
lst2 = lst1.copy()  # 拷贝. 浅拷贝 拷贝第一层
lst1[4].append("大阳哥")  #对第二次的列表进行增加操作
print(lst1, lst2)
# ['超人', '七龙珠', '葫芦娃', '山中小猎人', ['金城武', '王力宏', '渣渣辉', '大阳哥']] 
# ['超人', '七龙珠', '葫芦娃', '山中小猎人', ['金城武', '王力宏', '渣渣辉', '大阳哥']]

   深度拷贝. 把元素内部的元素完全进行拷贝复制. 不会产生一个改变另一个跟着改变的问题.

  语法  import copy

      copy.deepcopy()

import copy
lst1 = ["超人", "七龙珠", "葫芦娃", "山中小猎人", ["金城武", "王力宏", "渣渣辉"]]
lst2 = copy.deepcopy(lst1)  # 把lst1扔进去进行深度拷贝 , 包括内部的所有内容进行拷贝
lst1[4].append("大阳哥")
print(lst1, lst2)
# ['超人', '七龙珠', '葫芦娃', '山中小猎人', ['金城武', '王力宏', '渣渣辉', '大阳哥']]
# ['超人', '七龙珠', '葫芦娃', '山中小猎人', ['金城武', '王力宏', '渣渣辉']]

 

posted @ 2018-07-10 16:42  这里有个博客  阅读(388)  评论(0编辑  收藏  举报