zoukankan      html  css  js  c++  java
  • python 生成器函数.推导式.生成器表达式

    一.生成器

      什么是生成器,生成器的实质就是迭代器

      在python中有三种方式来获取生成器:

        1.通过生成器函数

        2.通过各种推导式来实现生成器

        3.通过数据的转换也可以获取生成器

    1 def func()
    2     print("111")
    3     yield 222
    4 ret = func()
    5 print(ret)
    6 
    7 结果:
    8 <generator object func at 0x10567ff68>

       send方法和__next__()

       send和__next__()一样都可以让生成器执行到下一个yield.

     1 def eat():
     2     print("我吃什么啊")
     3     a = yield "馒头"
     4     print("a=",a)
     5     b = yield "大饼"
     6     print("b=",b)
     7     c = yield "韭菜盒子"
     8     print("c=",c)
     9     yield "GAME OVER"
    10 gen = eat() # 获取生成器器
    11 ret1 = gen.__next__()
    12 print(ret1)
    13 ret2 = gen.send("胡辣汤")
    14 print(ret2)
    15 ret3 = gen.send("狗粮")
    16 print(ret3)
    17 ret4 = gen.send("猫粮")
    18 print(ret4)

        send和__next__() 的区别:

        1.send和next()都是让生成器向下走一次

        2.send可以让上一个yield的位置传递值,不能给最后一个yield发送值,在第一次执行生成器代码的时候不能用send()

        生成器可以使用for循环来获取内部元素:

     1 def func():
     2     print(111)
     3     yield 222
     4     print(333)
     5     yield 444
     6     print(555)
     7     yield 666
     8 gen = func()
     9 for i in gen:
    10     print(i)
    11 
    12 
    13 结果:
    14 111
    15 222
    16 333
    17 444
    18 555
    19 666


    二.列表推导式,生成器表达式以及其他推导式

      首先给出如下代码

    1 lst = []
    2 for i in range(1,15)
    3     lst.append(i)
    4 print(lst)

      替换成列表推导式:

    1 lst = [i for i in range(1,15)]
    2 print(lst)

      语法:

        [结果 for 变量 in 可迭代对象 if 条件]

      列表推导式可对结果进行筛选:

    1 lst = [i for i in range(1,15) if i%2 ==0]
    2 print(lst)

      生成器表达式与列表推导式的语法是一致的,只是把[]替换成了()

    1 gen = (i for i in range(1,15))
    2 print(gen)
    3 
    4 结果:
    5 <generator object <genexpr> at 0x106768f10>

      打印的结果是一个生成器,我们可以通过for循环来循环这个生成器:

    1 gen = (i for i in range(10))
    2 for i in gen:
    3     print(i)

      生成器表达式同样可以进行筛选:

    1 #获取1-100内能被3整除的数
    2 gen = (i for i in range(1,100) if i %3 == 0)
    3 
    4 for num in gen:
    5     print(num)

      生成器表达式和列表推导式的区别:

      1.列表推导式比较耗内存,一次性加载,生成器表达式几乎不占用内存,使用的时候采配合使用内存

        2.得到的值不一样,列表推导式得到的是一个列表,生成器表达式获取的是一个生成器.

      生成器的惰性机制:

     1 def func()
     2     print("111")
     3     yield 222
     4 
     5 g = func()  #生成器g
     6 g1 = (i for i in g) #生成器g1,但是生成器的数据来源于g
     7 g2 = (i for i in g1)  #生成器g2,来源于g1
     8 
     9 print(list(g))  #获取g中的数据,这时func()才会被执行,打印,获取到222,g完毕
    10 print(list(g1))  #获取g1中的数据,g1的数据来源于g,但是g已经取完,g1也没有数据
    11 print(list(g2))  #与g1同理

      字典推导式:

      

     1 # 把字典中的key和value互换
     2 dic = {'a': 1, 'b': '2'}
     3 new_dic = {dic[key]: key for key in dic}
     4 print(new_dic)
     5 
     6 # 在以下list中. 从lst1中获取的数据和lst2中相对应的位置的数据组成一个新字典
     7 lst1 = ['jay', 'jj', 'sylar']
     8 lst2 = ['周杰伦', '林俊杰', '邱彦涛']
     9 dic = {lst1[i]: lst2[i] for i in range(len(lst1))}
    10 print(dic)

      集合推导式:

        集合推导式可以帮我们直接生成一个集合,集合的特点:无序,不重复,所以集合推导式自带去重功能

    1 lst = [1, -1, 8, -8, 12]
    2 # 绝对值去重
    3 s = {abs(i) for i in lst}
    4 print(s)

      生成器表达式:

     1 def add(a, b):
     2     return a + b
     3 
     4 def test():
     5     for r_i in range(4):
     6         yield r_i
     7 g = test()
     8 
     9 for n in [2, 10]:
    10     g = (add(n, i) for i in g)
    11 
    12 print(list(g))

    结果:
    [20,21,22,23]

      生成器的惰性机制

  • 相关阅读:
    最大流——poj3308 (模板)
    混合边的欧拉路径——poj1637 最大流
    JBPM FAQ
    spring 读取资源文件方法
    JBPM使用assignHandler进行用户分派思路
    直接修改jpbm xml流程定义字段的方法
    转 java 读取文件的字符集
    JAVA实现AD验证
    找到一篇jbpm session closed解决办法的文章
    dwr 读取cookie
  • 原文地址:https://www.cnblogs.com/baijinshuo/p/9470470.html
Copyright © 2011-2022 走看看