master
/ 6.2.2 列表的更新.ipynb

6.2.2 列表的更新.ipynb @masterview markup · raw · history · blame

Notebook

6.4 列表的更新

赋值语句是改变对象值的最简单的方法,在列表中,也可以通过索引赋值改变列表中指定序号元素值。

1.索引赋值的方法为:

In [ ]:
ls[i] = a

其中i 为列表中的元素序号,要求i为整数且在列表序号范围内(-len(ls) <= i < len(ls)),当i值超出列表序号范围时,抛出错误:IndexError: list assignment index out of range。 a 为新值,其值可以与列表中原有元素的数据类型相同,也可以是不同的数据类型,甚至可以是一个列表或元组。

In [ ]:
ls = [88,56,95,46,100,77]  # 通过赋值创建列表L
ls[2] = 66
print(ls)                  # 序号为2的元素被替换为66,输出:[88, 56, 66, 46, 100, 77]

ls[3] = 'pass'             # 序号为3的元素赋字符串类型新值
print(ls)                  # 序号为3的元素被替换,输出:[88, 56, 66, 'pass', 100, 77]

ls[5] = ['True','False']   # 序号为5的元素赋列表类型新值
print(ls)                  # 序号为5的元素被替换, [88, 56, 66, 'pass', 100, ['True', 'False']]

除了按索引赋值以外,还可以用切片赋值的方法更新列表中的数据,切片赋值要求新值也为列表。
其操作相当于将原列表中切片中元素删除,同时用新的列表中的元素代替切片的位置。
当切片连续时(如ls[i:j]),此时新列表长度不限,可为空列表、与切片等长列表或超出切片长度的列表。

当切片不连续时(如,ls[i:j:step]),要求新列表与切片元素数量相等,再按顺序一一替换。

In [ ]:
ls = [88,56,95,46,100,77]  # 通过赋值创建列表ls
print(ls)                  # 输出原列表中元素[88, 56, 95, 46, 100, 77]

ls[1:3] =[33,44]           # 序号为1和2的元素被替换为新列表中的33和44
print(ls)                  # 输出:[88, 33, 44, 46, 100, 77]

ls[1:3] = []               # 序号为1和2的元素被替换为新列表中空值
print(ls)                  # 输出[88, 46, 100, 77],列表长度减少2

ls = [88,56,95,46,100,77]  # 通过赋值创建列表ls
ls[1:3] =[33,44,55,66]     # 序号为1和2的元素被替换为33、44、55、66
print(ls)                  # 输出[88, 33, 44, 55, 66, 46, 100, 77],列表长度增加2
In [ ]:
ls = [88, 56, 95, 46, 100, 77]  # 通过赋值创建列表ls
print(ls[0:6:2])                # 切片返回结果,3个元素,输出[88, 95, 100]

ls[0:6:2] = [10, 20, 30]        # 将切片返回的3个元素用新列表中对应位置的元素替代
print(ls)                       # 输出[10, 56, 20, 46, 30, 77]

ls = [88, 56, 95, 46, 100, 77]  # 通过赋值创建列表ls
ls[0:6:2] = ['Python', 'C语言', 'VB']  # 新列表元素的数据可为任意类型
print(ls)                       # 输出['Python', 56, 'C语言', 46, 'VB', 77]

如果输出id(ls)查看每次操作前后列表ls的id,可以发现,当列表长度没有增加且新加入的数据类型与原数据类型相同时,更新前后列表的id没有发生变化,也就是说,此时的更新是原地操作。而当更新列表后长度增加的操作,或更新后新加入的数据的类型与原数据类型不同时,更新前后列表的id会发生变化。也就是说,此时的更新是重新创建了新的列表,并将原列表和更新的数据一起放入新列表。
可以这样理解列表被创建后,就不能再往列表中增加元素了,如需增加新的元素,需要将整个列表中的元素复制一遍,再添加需要增加的元素。

2.为了解决这个问题,python提供了三种方法向列表中添加元素:

append()
extend()
insert()

这三种方法都是原地操作,不影响列表在内存中的起始地址。

2.1 append()在列表末尾添加一个元素,

append()方法的使用方式为:

In [ ]:
ls.append(x)  
# ls为操作的列表名,x为增加的元素。  
# 相当于: 
a[len(a):] = [x]
In [ ]:
ls = [88, 56, 95, 46, 100, 77]  # 通过赋值创建列表ls
ls.append(100)                  # 在原列表末尾增加新元素数字100
print(ls)                       # 输出[88, 56, 95, 46, 100, 77, 100]

ls = [88, 56, 95, 46, 100, 77]  # 通过赋值创建列表ls
ls[len(ls):] = [100]            # 在原列表末尾增加新元素数字100
print(ls)                       # 输出[88, 56, 95, 46, 100, 77, 100]

ls.append('python')             # 在原列表末尾增加新元素字符串'python'
print(ls)                       # 输出[88, 56, 95, 46, 100, 77, 100, 'python']

如果输出id(ls)可以发现,应用append()方法向列表中增加元素时,可以增加同类型元素,也可以增加不同类型元素,其列表的id不变,说明只是修改了原列表而没有重建列表。

2.2 extend()是将另一个可迭代对象转为列表并追加到当前列表的末尾

extend()方法的使用方式为:

In [ ]:
ls.extend(iterable) 
# 相当于:  
ls[len(ls):] = iterable
In [ ]:
ls = [88, 56, 95, 46, 100, 77]
L = [10, 20, 30]
ls.extend(L)  # 在原列表末尾增加新列表中的元素10,20,30
print(ls)     # 输出[88, 56, 95, 46, 100, 77, 10, 20, 30]

ls = [88, 56, 95, 46, 100, 77]
L = [10, 20, 30]
ls[len(ls):] = L  # 在原列表末尾增加新列表中的元素10,20,30
print(ls)         # 输出[88, 56, 95, 46, 100, 77, 10, 20, 30]
In [ ]:
ls = [88, 56, 95, 46, 100, 77]
ls.extend(range(5))  # 在原列表末尾增加新列表中的元素0, 1, 2, 3, 4
print(ls)     # 输出[88, 56, 95, 46, 100, 77, 0, 1, 2, 3, 4]

ls = [88, 56, 95, 46, 100, 77]
ls[len(ls):] = range(5)  # 在原列表末尾增加新列表中的元素0, 1, 2, 3, 4
print(ls)         # 输出[88, 56, 95, 46, 100, 77, 0, 1, 2, 3, 4]

与ls.extend(L)功能类似的一个操作是赋值运算+=:

In [ ]:
ls = [88, 56, 95, 46, 100, 77]
L = [10, 20, 30]

ls += L    # 不创建新对象,在原列表末尾增加新列表中的元素10,20,30
print(ls)  # 输出[88, 56, 95, 46, 100, 77, 10, 20, 30]

+=运算符会调用iadd方法,该方法的参数类型是可迭代对象(iterable),也就是说,L的类型并不局限于列表,可以是元组、range、字符串、集合和字典等,会先将其它类型的对象转为列表类型,再附加到列表的末尾。

In [ ]:
ls = [88, 56, 95, 46, 100, 77]
L1 = {35,65}
L2 = range(10, 30, 10)
L3 = (1, 2, 3)
L4 = "abc"

ls += L1    # 不创建新对象,在原列表末尾增加集合中的元素35,65
print(ls)   # 输出[88, 56, 95, 46, 100, 77, 35, 65]
ls += L2    # 不创建新对象,在原列表末尾增加新列元素10,20
print(ls)   # 输出[88, 56, 95, 46, 100, 77, 35, 65, 10, 20]
ls += L3    # 不创建新对象,在原列表末尾增加新元组中的元素1,2,3
print(ls)   # 输出[88, 56, 95, 46, 100, 77, 35, 65, 10, 20, 1, 2, 3]
ls += L4    # 不创建新对象,在原列表末尾增加新字符串中的元素a,b,c
print(ls)   # 输出[88, 56, 95, 46, 100, 77, 35, 65, 10, 20, 1, 2, 3, 'a', 'b', 'c']

2.3 insert()是向列表中任意位置插入一个一元素,insert()方法的使用方式为:

ls.insert(i,x)
ls为操作的列表名,i为插入位置的序号,x为增加的元素。

In [ ]:
ls.insert(0, x)    # 在列表开头插入元素

ls.insert(len(ls), x)
# 等同于 
ls.append(x)
In [5]:
ls = [88,56,95,46,100,77]  
ls.insert(2,99)     # 在序号为2的位置插入新值99
print(ls)           # 输出[88, 56, 99, 95, 46, 100, 77]
[88, 56, 99, 95, 46, 100, 77]
In [ ]: