生成器进阶、生成器表达式
一、生成器
从生成器中取值的几个方法:
- next()
- for
- 数据类型的强制转换(占用内存)
def func(): print(111) s = yield "aaa" print(s) print(222) yield "bbb" g = func() ret = next(g) # 111 print(ret) # aaa ret = g.send("xxx") # xxx 222 print(ret) # bbb
send()获取下一个值的效果和next()基本一致;只是在获取下一个值的时候,给上一个yield的位置传递一个数据。
使用send的注意事项:
- 第一次使用生成器的时候,必须使用next获取下一个值
- 最后一个yield不能接受外部的值
yield from:从相应内容中拆开一个一个返回
def func(): a = "123" b = ["a", "b", "c"] c = {"k1": "v1", "k2": "v2"} yield from a yield from b yield from c ret = func() for i in ret: print(i)
二、列表表达式、生成器表达式
ret = (i for i in range(5)) print("**", next(ret)) print("**", next(ret)) for i in ret: print("==", i)
得到生成器后,可用next()一个一个取,但最好是使用for循环取值。
各种推导式:
[每一个元素或和元素的相关操作 for 元素 in 可迭代数据类型] # 遍历之后挨个处理 [满足条件元素的相关操作 for 元素 in 可迭代数据类型 if 元素相关的条件] # 筛选功能
# 20以内所有能被3整除的数 ret = [i for i in range(20) if i % 3 == 0] print(ret) g = (i for i in range(20) if i % 3 == 0) for i in g: print(i)
# 找到嵌套列表中名字含有两个"e"的所有名字 names = [["Tom", "Jefferson", "Joe", "Wesley"],["Jill", "Jennifer"]] ret = [name for item in names for name in item if name.count("e") == 2] g = (name for item in names for name in item if name.count("e") == 2)
# 求L = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]中子列表第三个元素对应位置组成的列表 L = [[1, 2, 3], [4, 5, 6], [7, 8, 9]] l = [i[2] for i in L] print(l) # [3, 6, 9]
# 将一个字典的key和value对调 dic = {"a": 10, "b": 20} dic_ = {dic[k]: k for k in dic} print(dic_)
# 合并大小写对应的value值,将k统一成小写 dic = {"a": 10, "b": 20, "A": 10} dic_ = {k.lower(): dic.get(k.lower(), 0) +dic.get(k.upper(), 0) for k in dic} print(dic_)
# 集合推导式,结果自动去重 set_= {x**2 for x in [1, -1, 2]} print(set_)
生成器实现:有一个文件,从文件里分段读取内容,在读出来的内容前面加 ***,再返回给调用者
def func(): with open("1.txt", "r", encoding="utf-8") as f: for line in f: yield "***" + line.strip() g = func() for i in g: print(i)
三、生成器相关面试题
面试题1:
def func(): for i in range(4): yield i g = func() g1 = (i for i in g) g2 = (i for i in g1) print(list(g1)) #[0, 1, 2, 3] print(list(g2)) #[]
面试题2:
def add(n, i): return n + i def test(): for i in range(4): yield i g = test() for n in [1,10]: g=(add(n,i) for i in g) print(list(g)) # [20, 21, 22, 23]