文章目录
列表(list)
列表推导式
列表推导式在内部实际上是一个循环结构,只是形式更简洁
(1)
a = [i*i for i in range(10)]
相当于
a = []
for i in range(10):
a.append(i*i)
也相当于
a = list(map(lambda i: i*i, range(10)))
(2)
a = [' ab', 'cd ']
a = [x.strip() for x in a] # 删除两端的空白字符
相当于
a = [' ab', 'cd ']
for i,v in enumerate(a):
a[i] = v.strip()
也相当于
a = [' ab', 'cd ']
a = list(map(str.strip, a))
(3)
def add(v):
return v+5
print([add(i) for i in range(1, 4)])
(4)
使用列表推导式实现嵌套列表的平铺
a = [[1, 2, 3], [4, 5,6], [7, 8, 9]]
print([n for elem in a for n in elem]) # 左外右内
相当于
a = [[1, 2, 3], [4, 5,6], [7, 8, 9]]
result = []
for elem in a:
for n in elem:
result.append(n)
print(result)
也就是
a = [[1, 2, 3], [4, 5,6], [7, 8, 9]]
result = []
for elem in a:
result += elem
print(result)
还可以是
a = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
print(sum(a, []))
from itertools import chain
a = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
print(list(chain(*a)))
# chain串联多个迭代对象来形成一个更大的迭代对象
如果不确定嵌套层数,可以这样做:
def take_out(arr):
for item in arr:
if isinstance(item, int):
result.append(item)
else:
take_out(item) # 递归
data = [[[1], [2], [3]], [[4], [5], [6]], [[7], [8], [9]]]
result = []
take_out(data)
print(result)
列表推导式中可以在最后加入if语句,删选符合要求的元素
vec = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
print([num for elem in vec for num in elem\
if num % 5 == 0 or num % 3 == 0])
import os
print([filename for filename in os.listdir('.') if filename.endswith(('.py', '.pyw'))])
筛选出当前目录下后缀为.py或.pyw的文件名
在列表推导式中使用多个循环,实现多序元素的任意组合
print([(x, y) for x in range(3) for y in range(3)])
列表推导式可以使用函数或复杂表达式
print([v**2 if v % 2 == 0 else v+1 for v in [2, 3, 4, -1] if v > 0])
x = list(range(5))
print([item > 2 for item in x])
使用列表推导式生成100以内的所有素数
print([p for p in range(100) if 0 not in [p%d for d in range(2, int(p**0.5)+1)]])
切片操作
通过切片操作,相当于得到一个子列表.
使用[ : ]
的方式进行切片操作
a = [1, 2, 3, 4]
print(a[1:3])
[1 : 3]
中的 1 : 3
表示的是 [1 ,3)
这样的由下标构成的前闭后开
的区间
下标还可以是负数, -1相等于 len(a) -1
a = [1, 2, 3, 4]
print(a[1:-1])
切片操作可以省略前后边界
- 省略后边界,表示获取到列表末尾
- 省略前边界,表示从列表开头获取
- 省略两个边界,表示获取整个列表
切片操作还可以指定步长
多加一个 : , 再多加一个数字,这个数字就是步长.
a = [1, 2, 3, 4]
print(a[::2])
步长可以是负数,前面的范围要求前大后小,不然显示是空的,而且前面的两个参数像是交换了一下位置,还是前闭后开.
a = [1, 2, 3, 4]
print(a[3:0:-1])
当切片中的范围超出有效下标不会出现异常!
而是尽可能把符合要求的元素给取到
切片整体可以支持下标操作
a = [1, 2, 3, 4]
print(a[::2][1])
可以使用切片来原地修改列表的内容
a = [4, 6, 7]
a[len(a):] = [9] # 在末尾追加元素
print(a)
a[:3] = [1, 2, 3] # 替换前3个元素
print(a)
a[:3] = [] # 删除前3个元素
print(a)
a = list(range(10))
print(a)
a[::2] = [0]*5 # 替换偶数位置的元素
print(a)
使用del 与切片结合来删除列表元素
a = [1, 2, 3, 4, 5, 6]
del a[:3] # 删除前3个元素
print(a)
遍历
1.for 循环(依次取出单个元素)
a = [1, 2, 3, 4]
for elem in a:
print(elem)
无法通过elem改a中的元素
2.for 循环(下标的方式)
a = [1, 2, 3, 4]
for i in range(0, len(a)):
print(a[i])
可以通过a[ i ] 修改元素
新增元素
1.使用 append 方法,向列表末尾插入一个元素
a = [1, 2, 3, 4]
a.append('hello')
print(a)
2.使用 insert 方法,向任意位置插入一个元素
insert 第一个参数表示要插入元素的下标
a = [1, 2, 3, 4]
a.insert(1, 'hello')
print(a)
3.使用*运算符将包含子列表的列表重复时,并不是复制子列表值,而是复制已有元素的引用.因此,当修改其中一个值时,相应的引用也会被修改.
x = [[1]*2]*3
print(x)
x[0][0] = 2
print(x)
不包含子列表的列表就没有问题!!
查找元素
1.使用 (not) in 操作符,判定元素是否在列表中存在,返回布尔类型
a = [1, 2, 3, 4]
print(2 in a)
使用 index 方法,查找元素第一次出现在列表中的下标,返回值是一个整数.如果元素不存在,则会抛出异常
a = [1, 2, 3, 4]
print(a.index(2))
print(a.index(10))
删除元素
1.使用 pop 方法删除并返回指定下标(默认是最后一个)的元素
- 删除最末尾的元素
a = [1, 2, 3, 4]
a.pop()
print(a)
- 按照下标来删除元素
a = [1, 2, 3, 4]
a.pop(2)
print(a)
2.使用 remove 方法,按照值删除首次出现的指定元素
a = [1, 2, 3, 4, 2]
a.remove(2)
print(a)
3.使用 del 命令删除列表中指定下标的元素
a = [1, 2, 3, 4]
del a[1] # 删除下标为1的元素
print(a)
列表的拼接
1.使用 + 能够把两个列表拼接在一起(不会影响到旧列表的内容)
a = [1, 2, 3, 4]
b = [5, 6, 7, 8]
print(a+b)
2.使用 extend 方法,相当于把一个列表拼接到另一个列表后面.
a.extend(b),是把 b中的内容拼接到 a 的末尾,不会修改 b,但是会修改 a.
a = [1, 2, 3, 4]
b = [5, 6, 7, 8]
a.extend(b)
print(a)
print(b)
extend 方法是没有返回值的
None 表示啥都没有.(类似于C里面的NULL,或者Java 里的 null)
3.使用 += 类似于extend 方法,+=后面可以不是列表
x = []
x += '12'
print(x)
x += '12’不等于 x = x+‘12’
清空列表
使用 clear 方法删除列表中的所有元素,但保留列表对象
a = [1, 2, 3, 4]
a.clear()
print(a)
使用 count 方法统计指定元素在列表中出现的次数
a = [1, 5, 5, 4, 7, 7.4]
print(a.count(5))
print(a.count(8))
def check(s1, s2):
return sum(map(s1.count, s2))
print(check('*******,,,,,....', ',*&'))
,和*总共12个
enumerate(列表):枚举列表元素,返回枚举对象,其中每个元素为包含下标和值的元组.该函数对元组/字符串同样有效
a = []
for item in enumerate([3, 4, 5]):
a.append(item)
print(a)
使用 sort ( ) 方法进行原地排序
from random import shuffle
a = list(range(16))
shuffle(a)
print(a)
a.sort(reverse=True) # 降序排序
print(a)
a.sort(key=lambda x:len(str(x))) # 按转换成字符串的长度排序,同类型保持原来的顺序
print(a)
元组(tuple)
元组的功能和列表基本是一致的.
但元组不能修改里面的元素,列表则可以
因此,读操作(访问下标,切片,遍历,in,index,+,count()等)元组也是一样支持的
但,写操作(修改元素,新增元素,删除元素,extend等),元组不能支持
另外,元组在Python中很多时候是默认的集合类型,例如,当一个函数返回多个值的时候
def getPoint():
return 10, 20
result = getPoint()
print(type(result))
结果是
元组相对于列表来说,优势有多方面:
- 不会把数据弄乱,安全很多
- 元组(不包含可变对象)可以作字典的键,或作为集合的元素,而列表和包含可变对象的元组不行
元组的访问速度比列表要快一些,如果定义了一系列常量值,并且主要用途仅仅是对其进行遍历二不需要进行任何修改,建议使用元组而不使用列表。
from timeit import timeit # 计时模块
print(timeit('[1, 2, 3]'))
print(timeit('(1, 2, 3)'))
此例中,元组的创建速度仅是列表的四分之一
from sys import getsizeof
print(getsizeof([1, 2, 3]))
print(getsizeof((1, 2, 3)))
此例中,元组比列表少占用一些空间
如果元组只有一个元素的话,后面的逗号不能省略
可以这样创建元组
a = 3,
print(a)
使用del可以删除元组对象,不能删除元组的元素
字典(dict)
字典的各种操作,都是针对 key 来进行的.
最后一个键值对后面的,可写可不写.
globals()返回包含当前作用域内所有全局变量和值的字典
locals()返回包含当前作用域内所有局局变量和值的字典
创建字典
使用dict利用已有数据创建字典
keys = ['a', 'b', 'c', 'd']
values = [1, 2, 3, 4]
x = dict(zip(keys, values))
print(x)
使用dict根据给定的键,值创建字典
x = dict(name='zhangsan', age=37)
print(x)
以给定内容为键,创建值为空的字典
x = dict.fromkeys(['name', 'age', 'sex']) # 以列表中的元素作为键
print(x)
字典推导式
s = {x: x.strip() for x in (' he ', 'she ', ' I')}
# 原字符串作为键,删除字符串前面和后面的空格作为字典的值
print(s)
for k, v in s.items():
print(k, ':', v)
x = ['A', 'B', 'C', 'D']
y = ['a', 'b', 'c', 'd']
print({i: j for i, j in zip(x, y)})
查找元素
1.使用 in可以判定 键 是否在 字典 中存在,返回布尔值
student = {
'id': 1,
'name': '张三'
}
print('id' in student)
print('score' in student)
2.使用 [ ] 通过类似于取下标的方式,获取到元素的值,只不过此处的’下标’是键(键可以是整数,也可以是字符串等其他类型)
student = {
'id': 1,
'name': '张三',
}
print(student['id'])
print(student['name'])
如果key 在字典中不存在,则会抛出异常.
使用字典对象的get()方法获取指定键对应的值,并且可以在键不存在的时候返回指定值
x = {
'name': 'zhangsan',
'sex': 'male',
'age': 37
}
print(x.get('name'))
print(x.get('address')) # 指定键不存在,也没有第2个参数,返回None
print(x.get('address', 'ZAFU'))
print(x)
新增/修改元素
使用[ ] 可以根据key 来新增/修改 value(值)
- 如果 key 不存在,即为新增键值对
student = {
'id': 1,
'name': '张三',
}
student["score"] = 90
print(student)
- 如果 key 已经存在,即为修改键值对的值
student = {
'id': 1,
'name': '张三',
'score': 10
}
student["score"] = 90
print(student)
使用字典对象的update()方法将另一个字典的键值对添加或覆盖到当前字典对象.
x = {
'name': 'zhangsan',
'age': 37,
'score': [98, 97]
}
x.update({
'a': 'a',
'age': 43
})
print(x)
删除元素
使用 pop() 方法根据 key 删除对应的键值对并返回指定键的元素
student = {
'id': 1,
'name': '张三',
'score': 10
}
print(student.pop('id'))
print(student)
使用字典对象的popitem()方法删除并返回字典中最后一个元素
x = dict.fromkeys(['name', 'age', 'sex'])
print(x.popitem())
print(x)
使用del删除整个字典,也可以删除某个元素
x = dict.fromkeys(['name', 'age', 'sex']) # 以列表中的元素作为键
del x['name'] # 删除键为'name'的元素
print(x)
del x # 删除整个字典
使用字典对象的clear()方法来删除字典中所有元素
x = dict.fromkeys(['name', 'age', 'sex'])
x.clear()
print(x)
遍历字典元素
- 在C++ 或者 Java 中,哈希表里面的键值对存储的顺序是无序的!
- 而Python中做了特殊处理,保证遍历出来的顺序和插入的顺序是一致的.
直接使用 for 循环能够获取到字典中所有的 key,进一步就可以取出每个值了
student = {
'id': 1,
'name': '张三',
'score': 10
}
for key in student:
print(key, student[key])
取出所有的 key 和 value
1.使用 keys 方法可以获取到字典中所有的 key
student = {
'id': 1,
'name': '张三',
'score': 10
}
print(student.keys())
此处 dict_keys
是一个特殊的类型,专门用来表示字典中所有的 key ,大部分元组支持的操作对于 dict_keys
同样适用
2.使用 values 方法可以获取到字典中所有的 value
student = {
'id': 1,
'name': '张三',
'score': 10
}
print(student.values())
3.使用 items 方法可以获取到字典中所有的键值对
student = {
'id': 1,
'name': '张三',
'score': 10
}
print(student.items())
student = {
'id': 1,
'name': '张三',
'score': 10
}
for key, value in student.items():
print(key, value)
all()和any()
all() 函数用来测试列表,元组等序列对象以及map对象,zip对象等类似对象中是否所有元素都等价于True,any()函数用来测试序列或可迭代对象中是否存在等价于True的元素.
print(all([1, 2]))
print(all([1, 0]))
print(any([1, 0]))
print(any([0]))
a = 'abcdef'
print(any(map(lambda x: x in a, ['c', 'h'])))
print(any(map(lambda x: x in a, ['i', 'h'])))