0%

Python - Theme 3 Advanced Character

1. 切片

Python提供了切片(Slice)操作符,常用来取一个list或者tuple的部分元素。有了切片,就可以用一行代码代替多行循环了。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
>>> L = list(range(10))
>>> L[0:3] ##按照元素的索引切片
[0, 1, 2]
>>> L[:3] ##从第0个元素开始,第3个结束
[0, 1, 2]
>>> L[1:3] ##从第1个元素开始
[1, 2]
>>> L[:-2] ##倒数第2个元素结束
[0, 1, 2, 3, 4, 5, 6, 7]
>>> L[:5] ##取前5个
[0, 1, 2, 3, 4]
>>> L[-5:] ##取后5个
[5, 6, 7, 8, 9]
>>> L[:7:2] ##第0~7元素,每隔2个
[0, 2, 4, 6]
>>> L[::2] ##全部元素每隔2个
[0, 2, 4, 6, 8]
>>> L[:] ##相当于复制了一遍list
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>> (0, 1, 2, 3, 4, 5)[:3] ##切片tuple
(0, 1, 2)
>>> 'ABCDEFG'[::2] ##字符串也可以看做一种list
'ACEG'

2. 迭代

迭代(Iteration),我们一般用for循环来遍历一个list或者tuple,这种遍历我们称为迭代。只要是可迭代对象即可迭代。

1
2
3
4
5
6
7
8
9
10
##如何判断是否为可迭代对象
>>> from collections import Iterable
>>> isinstance('abc',Iterable) ##str是可迭代对象
True
>>> isinstance(['a','b','c'],Iterable) ##list是可迭代
True
>>> isinstance({'a':1,'b':2,'c':3},Iterable) ##dict是可迭代
True
>>> isinstance(123,Iterable) ##整数不可迭代
False

2.1. 迭代list

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
>>> L = ['a','b','c','d','e','f']
>>> for i in L:
>>> print(i)
a
b
c
d
e
f

##实现带下标输出
>>> for i,value in enumerate(L):
>>> print(i,value)
0 a
1 b
2 c
3 d
4 e
5 f

2.2. 迭代dict

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
d = {'a': 1, 'b': 2, 'c': 3}
##遍历key
>>> for key in d:
>>> print(key)
a
b
c

##遍历value
>>> for value in d.values():
>>> print(value)
1
2
3

##同时迭代k,v
>>>for k,v in d.items():
>>> print(k,v)
a 1
b 2
c 3

2.3. 迭代str

1
2
3
4
5
6
7
8
>>>for i in 'abcdef':
>>> print(i)
a
b
c
d
e
f

3. 列表生成式

列表生成式即List Comprehensions,是Python内置的非常简单却强大的可以用来创建list的生成式。

1
2
3
# x*x:要生成的元素写在前面; 后面直接跟for循环.
>>> [x*x for x in range(1,11)]
[1, 4, 9, 16, 25, 36, 49, 64, 81, 100]

3.1. For循环后面跟if判断

1
2
3
4
5
6
7
# if在for循环之后不能带else,因为在这里代表筛选条件
>>> [x*x for x in range(1,11) if x % 2 == 0]
[4, 16, 36, 64, 100]

# if在for循环之前必须带else,因为是表达式,必须根据x计算出一个结果
>>> [x if x % 2 == 0 else -x for x in range(1,11)]
[-1, 2, -3, 4, -5, 6, -7, 8, -9, 10]

3.2. 两层for循环; 很少用到三层及以上的循环

1
2
3
# 生成全排列
>>> [x + y for x in "abc" for y in "123"]
['a1', 'a2', 'a3', 'b1', 'b2', 'b3', 'c1', 'c2', 'c3']

3.3. For循环可以同时使用两个变量

1
2
3
>>> d = {'x': '1', 'y': '2', 'z': '3'}
>>> [k + '=' + v for k, v in d.items()]
['x=1', 'y=2', 'z=3']

4. 生成器

受到内存的限制,创建列表的容量是有限的,而且如果仅用到列表前几个元素,那么就白白浪费了空间。生成器(generator),是储存了列表元素的算法,形成了一边循环一边计算的机制,从而节省了空间。

4.1. 方法一

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
# 将列表生成式的[]改为()
>>> L = (x*2 for x in range(4))
>>> L
<generator object <genexpr> at 0x109ac12d0>
>>> next(L) # next()函数获得generator的下一个返回值
0
>>> next(L)
2
>>> L.__next__()
4
>>> L.__next__()
6
>>> L.__next__() # 直到最后一个元素,抛出 StopIteration 错误
Traceback (most recent call last):
File "<input>", line 1, in <module>
StopIteration

# 一般都使用for语句访问,next()只是用来说明用的
L = (x*2 for x in range(4))
>>> for i in L:
... print(i)
...
0
2
4
6

4.2. 方法二: yield语句

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
# 不使用生成器, 则先生成List, 后打印List
def gen_num():
nums = []
for i in range(4):
print('生成数据:', i)
nums.append(i)
return nums


nums = gen_num()
for num in nums:
print('打印数据:', num)

# 输出
生成数据: 0
生成数据: 1
生成数据: 2
生成数据: 3
打印数据: 0
打印数据: 1
打印数据: 2
打印数据: 3

# 使用生成器yield
def gen_num():
for i in range(4):
print('生成数据:', i)
yield i


nums = gen_num()
for num in nums:
print('打印数据:', num)

# 输出 - 边生成边输出
生成数据: 0
打印数据: 0
生成数据: 1
打印数据: 1
生成数据: 2
打印数据: 2
生成数据: 3
打印数据: 3

# 杨辉三角 --<代码精妙>
>>> def triangles():
... L = [1]
... while True:
... yield L
... L = [1] + [L[i]+L[i+1] for i in range(len(L)-1)] + [1]

5. 迭代器

5.1. Iterable 对象(列表、字典、字符串、生成器)

1
2
3
4
5
6
7
8
9
10
11
>>> from collections.abc import Iterable
>>> isinstance([], Iterable)
True
>>> isinstance({}, Iterable)
True
>>> isinstance('abc', Iterable)
True
>>> isinstance((x*2 for x in range(6)), Iterable)
True
>>> isinstance(10, Iterable) # 数字不可迭代
False

5.2. Iterator: 迭代器 - 可以被next()函数调用并不断返回下一个值的对象

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
# Iterator计算是惰性的,只有需要返回下一个数据时才计算。而且只能遍历一次。
>>> from collections.abc import Iterator
>>> isinstance((x*2 for x in range(6)), Iterator)
True
>>> isinstance([], Iterator)
False
>>> isinstance({}, Iterator)
False
>>> isinstance('abc', Iterator)
False

# iter()函数可以将 list, dict, str等变成 Iterator
>>> isinstance(iter([]), Iterator)
True
>>> isinstance(iter({}), Iterator)
True
>>> isinstance(iter('abc'), Iterator)
True