zoukankan      html  css  js  c++  java
  • day11

    二,生成器

    2.1初始生成器

    我们知道的迭代器有两种:一种是调用方法直接返回的,一种是可迭代对象通过执行iter方法得到的,迭代器有的好处是可以节省内存。

    如果在某些情况下,我们也需要节省内存,就只能自己写。我们自己写的这个能实现迭代器功能的东西就叫生成器。

     

    Python中提供的生成器:

    1.生成器函数:常规函数定义,但是,使用yield语句而不是return语句返回结果。yield语句一次返回一个结果,在每个结果中间,挂起函数的状态,以便下次重它离开的地方继续执行

    2.生成器表达式:类似于列表推导,但是,生成器返回按需产生结果的一个对象,而不是一次构建一个结果列表

     

    生成器Generator:

      本质:迭代器(所以自带了__iter__方法和__next__方法,不需要我们去实现)

      特点:惰性运算,开发者自定义

    2.2 生成器函数

    一个包含yield关键字的函数就是一个生成器函数。yield可以为我们从函数中返回值,但是yield又不同于return,return的执行意味着程序的结束,调用生成器函数不会得到返回的具体的值,而是得到一个可迭代的对象。每一次获取这个可迭代对象的值,就能推动函数的执行,获取新的返回值。直到函数执行结束。

    import time
    def genrator_fun1():
        a = 1
        print('现在定义了a变量')
        yield a
        b = 2
        print('现在又定义了b变量')
        yield b
    
    g1 = genrator_fun1()
    print('g1 : ',g1)       #打印g1可以发现g1就是一个生成器
    print('-'*20)   #我是华丽的分割线
    print(next(g1))
    time.sleep(1)   #sleep一秒看清执行过程
    print(next(g1))
    
    初识生成器函数

    生成器有什么好处呢?就是不会一下子在内存中生成太多数据

    假如我想让工厂给学生做校服,生产2000000件衣服,我和工厂一说,工厂应该是先答应下来,然后再去生产,我可以一件一件的要,也可以根据学生一批一批的找工厂拿。
    而不能是一说要生产2000000件衣服,工厂就先去做生产2000000件衣服,等回来做好了,学生都毕业了。。。

    def produce():
        """生产衣服"""
        for i in range(2000000):
            yield "生产了第%s件衣服"%i
    
    product_g = produce()
    print(product_g.__next__()) #要一件衣服
    print(product_g.__next__()) #再要一件衣服
    print(product_g.__next__()) #再要一件衣服
    num = 0
    for i in product_g:         #要一批衣服,比如5件
        print(i)
        num +=1
        if num == 5:
            break

    2.3 send

    def generator():
        print(123)
        content = yield 1
        print('=======',content)
        print(456)
        yield2
    
    g = generator()
    ret = g.__next__()
    print('***',ret)
    ret = g.send('hello')   #send的效果和next一样
    print('***',ret)
    
    #send 获取下一个值的效果和next基本一致
    #只是在获取下一个值的时候,给上一yield的位置传递一个数据
    #使用send的注意事项
        # 第一次使用生成器的时候 是用next获取下一个值
        # 最后一个yield不能接受外部的值

    三,列表推导式和生成器表达式

    l = [i for i in range(10)]
    print(l)
    l1 = ['选项%s'%i for i in range(10)]
    print(l1)

    1.把列表解析的[]换成()得到的就是生成器表达式

    2.列表解析与生成器表达式都是一种便利的编程方式,只不过生成器表达式更节省内存

    3.Python不但使用迭代器协议,让for循环变得更加通用。大部分内置函数,也是使用迭代器协议访问对象的。例如, sum函数是Python的内置函数,该函数使用迭代器协议访问对象,而生成器实现了迭代器协议,所以,我们可以直接这样计算一系列值的和:

    sum(x ** 2 for x in range(4))

     匿名函数

    匿名函数:为了解决那些功能很简单的需求而设计的一句话函数。

    #这段代码
    def calc(n):
        return n**n
    print(calc(10))
     
    #换成匿名函数
    calc = lambda n:n**n
    print(calc(10))

    上面是我们对calc这个匿名函数的分析,下面给出了一个关于匿名函数格式的说明

    函数名 = lambda 参数 :返回值
    
    #参数可以有多个,用逗号隔开
    #匿名函数不管逻辑多复杂,只能写一行,且逻辑执行结束后的内容就是返回值
    #返回值和正常的函数一样可以是任意数据类型

    我们可以看出,匿名函数并不是真的不能有名字。

    匿名函数的调用和正常的调用也没有什么分别。 就是 函数名(参数) 就可以了~~~

    匿名函数与内置函数举例:

    l=[3,2,100,999,213,1111,31121,333]
    print(max(l))
    
    dic={'k1':10,'k2':100,'k3':30}
    
    
    print(max(dic))
    print(dic[max(dic,key=lambda k:dic[k])])
    复制代码
    l=[3,2,100,999,213,1111,31121,333]
    print(max(l))
    
    dic={'k1':10,'k2':100,'k3':30}
    
    
    print(max(dic))
    print(dic[max(dic,key=lambda k:dic[k])])
    复制代码
    res = map(lambda x:x**2,[1,5,7,4,8])
    for i in res:
        print(i)
    res = filter(lambda x:x>10,[5,8,11,9,15])
    for i in res:
        print(i)
    作者:Mark.Yang

    -------------------------------------------

    个性签名:就算要出卖灵魂,也要找个付的起价钱的人

    如果觉得这篇文章对你有小小的帮助的话,记得在右下角点个“推荐”哦,博主在此感谢!

  • 相关阅读:
    「暑期集训day23」黑幕
    暑期集训day23考试整理
    「暑期集训day22」黑色
    暑期集训day22考试整理
    「暑期集训day21」往复
    「暑期集训day20」仰望
    日常报错
    Spring-Boot环境的快速搭建
    jsp和thymeleaf模板
    Boot的简单配置
  • 原文地址:https://www.cnblogs.com/yang950718/p/10268239.html
Copyright © 2011-2022 走看看