【主要内容】

1. 生成器和生成器函数
    生成器的本质就是迭代器
    生成器的三种创建办法:
        1.通过生成器函数
        2.通过生成器表达式创建生成器
        3.通过数据转换
    生成器函数:
        函数中包含了yield的就是生成器函数
        注意:生成器函数被执行. 获取到的是生成器. 而不是函数的执行
    生成器表达式:
        (结果 for 变量 in 可迭代对象 if 筛选)
    取值:
        1. __next__()
        2. send(值) 给上一个yield位置传一个值, 第一个和最后一个yield不用传值
        3. 可以for循环
        4. list(g)
2. 各种推倒式和生成器表达式
    1. 列表推倒式 [结果 for 变量 in 可迭代对象 if 筛选]
    2. 字典推倒式 {结果 for 变量 in 可迭代对象 if 筛选} 结果=>key:value
    3. 集合推倒式 {结果 for 变量 in 可迭代对象 if 筛选} 结果=>key

【代码】

1、生成器函数

1 # def func():
 2 #     print("我是周杰伦")
 3 #     yield "昆凌"  # 函数中包含了yield, 当前这个函数就不再是普通的函数了. 是生成器函数
 4 #     print("我是王力宏")
 5 #     yield "李云迪???"
 6 #     print("我是笛卡尔积")
 7 #     yield "笛卡尔积是谁"
 8     # print("你好啊") # 最后一个yield之后如果再进行__next__() 会报错
 9 # g = func()
10 # print(g.__next__())
11 # print(func().__next__())
12 #
13 # g1 = func()
14 # g2 = func()
15 # print(g1.__next__())
16 # print(g1.__next__())
17 #
18 # print("==============")
19 # print(g2.__next__())
20 
21 #
22 # g = func()  # 通过函数func()来创建一个生成器
23 # print(g.__next__()) # 周杰伦
24 # print(g.__next__()) # 王力宏
25 # print(g.__next__()) # 笛卡尔积
26 # print(g.__next__())
27 
28 # return 直接返回结果. 结束函数的调用
29 # yield 返回结果.可以让函数分段执行
30 #
31 # def func():
32 #     lst = []
33 #     for i in range(1,100001):
34 #         lst.append("衣服%s" % i)
35 #     return lst
36 #
37 # def gen():
38 #     i = 1
39 #     while i < 100001:
40 #         yield "衣服%s" % i
41 #         i = i + 1
42 # g = gen()
43 # print(g.__next__())
44 # print(g.__next__())
45 # print(g.__next__())
46 # print(g.__next__())
47 # print(g.__next__())
48 # print(g.__next__())
49 
50 #
51 # def func():
52 #     yield 11
53 #     yield 22
54 #     yield 33
55 #     yield 44
56 #
57 #
58 # g = func()  # 拿到的是生成器. 生成器的本质是迭代器. 迭代器可以被迭代 生成器可以直接for循环
59 #
60 # for i in g:
61 #     print(i)    # 本质上执行的是__next__()
62 #
63 # it = g.__iter__()
64 # while True:
65 #     try:
66 #         print(it.__next__())
67 #     except StopIteration:
68 #         break

2、send

1 # def func():
 2 #     print("大碴粥")
 3 #     a = yield "11"
 4 #     print(a)
 5 #     print("狗不理")
 6 #     b = yield "22"
 7 #     print(b)
 8 #     print("大麻花")
 9 #     c = yield "33"
10 #     print(c)
11 #
12 # g = func()
13 # print(g.__next__())
14 # print(g.send(1))
15 # print(g.send(2))
16 # print(g.send(3))
17 
18 # __next__() 可以让生成器向下执行一次
19 # send() 也可以让生成器向下执行一次, 给上一个yield传一个值, 第一个不能用send(). 最后一个也不要传值
20 
21 
22 def eat():
23     print("我吃什么啊")
24     a =  yield  "馒头"
25     print("a=",a)
26     b =  yield  "大饼"
27     print("b=",b)
28     c =  yield  "韭菜盒子"
29     print("c=",c)
30     yield  "GAME OVER"
31 
32 gen = eat()      # 获取⽣成器
33 
34 ret1 = gen. __next__ ()
35 print(ret1)
36 ret2 = gen.send("胡辣汤")
37 print(ret2)
38 ret3 = gen.send("狗粮")
39 print(ret3)
40 ret4 = gen.send("猫粮")
41 print(ret4)
42 
43 
44 def func():
45     yield 11
46     yield 22
47     yield 33
48     yield 44
49 g = func()
50 lst = list(g)   # 可迭代对象
51 print(lst)

3、推导式

1 # 生成列表 里面装1-14的数据
 2 # lst = []
 3 # for i in range(1,15):
 4 #     lst.append("python%s" % i)
 5 # print(lst)
 6 
 7 # 列表推倒式; 最终给你的是列表
 8 # 语法 [最终结果(变量) for 变量 in 可迭代对象]
 9 
10 # lst = [i for i in range(1,15)]
11 # print(lst)
12 
13 # [最终结果 for 变量 in 可迭代对象 if 条件]
14 lst = [i for i in range(1,101) if i%2==0]
15 print(lst)
16 
17 # 1. 获取1-100内能被3整除的数
18 # lst = [i for i in range(1,101) if i % 3 == 0]
19 # 2. 100以内能被3整除的数的平方
20 # lst = [i*i for i in range(1,101) if i % 3 == 0]
21 # 3. 寻找名字中带有两个e的⼈的名字
22 # names = [['Tom', 'Billy', 'Jefferson' , 'Andrew' , 'Wesley' , 'Steven' ,
23 # 'Joe'],['Alice', 'Jill' , 'Ana', 'Wendy', 'Jennifer', 'Sherry' , 'Eva']]
24 # lst = [name for first in names for name in first if name.count("e") == 2]
25 # print(lst)
26 #
27 # lst = ["衣服%s" % i for i in range(10000)]

4、生成器表达式

1 # g = (i for i in range(10))
 2 # print(list(g))
 3 
 4 # gen = ("麻花藤我第%s次爱你" % i for i in  range(10))
 5 # for i in  gen:
 6 #     print(i)
 7 
 8 # 生成器的惰性机制
 9 # def func():
10 #     print(111)
11 #     yield  222
12 # g = func()
13 # g1 = (i  for i in  g)
14 # g2 = (i  for i in  g1)
15 #
16 # print(list(g))
17 # print(list(g1))
18 # print(list(g2))

5、字典推导式+集合推导式

#字典推导式
# dic = {"a":"b", "c":"d"}
# # 把字典中的key:value互换 .{"b":"a", "d":"c"}
# new_dic = {dic[key]:key for key in dic}
# print(new_dic)

# lst1 = ["alex", "wusir", "taibai", "ritian"]
# lst2 = ['sb', "很色", "很白", "很牛"]
# # {"alex":"sb", "wusir":"很色"}
#
# dic = { lst1[i]:lst2[i] for i in range(len(lst1))}
# print(dic)

#集合推导式
lst = ["马化腾", "马化腾", "王建忠", "张建忠", "张建忠", "张雪峰", "张雪峰"]

s = {i for i in lst}    # 集合推倒式
print(s)

5、难度很大的题

# 一个面试题,难度很大
def add(a,b):
    return a + b
def test():
    for r_i in range(4):
        yield r_i
    #[0,1,2,3]
g = test()     #g是生成器
for n in [2, 10]:    # n=2,10
    g = (add(n, i) for i in g)
# 上面for循环等同于:(循环两次)  所有的n都是10(惰性机制)
#     g=(add(n,i) for i in (add(n,i) for i in test())
print(list(g))