首页 > 技术文章 > 函数之生成器的调用和生成器表达式

fangjie0410 2017-09-05 16:21 原文

一 生成器的调用方法

 生成器里面的值的只能按顺序调用一次,只能向前,不能后退。

 生成器里面的值只是在调用的时候才被执行。

# def aa():
#     yield from [1,2,3]
# a=aa()
# for i in a:
#     print(i)
#     print(list(a))

 send:1 和next的用法一样,执行生成器,执行时必须带一个参数

    2 send和next的起止位置完全相同,在生成器send关键字执行开始之前,需要先用next激活这个生成器。

    3 send可已将一个值当作信号量传递到函数中去

# def aaa():
#     print(123)
#     a=yield 1
#     print(a)
#     b=yield 2
#     print(b)
#     c=yield 3
#     print(c)
#     yield 4
# aa=aaa()
# print(aa.__next__())
# print(aa.send(10))
# print(aa.send(20))
# print(aa.send(30))

 如果yield前面有个变量的话,就用send执行,并传入一个值。

  只要用send传递参数的时候,必须在生成器中海油一个未被返回的yield。

二 列表推导式

  列表推导式就是将一些能简单执行的代码,用更简单的代码实现。

  列表推导式格式:print([返回结构 执行对象  if判断条件])

# print([i for i in range(30) if i%3==0])

 生成器表达式是在2.4中引入的新内容,它和列表解析的语法很像,但是在大 数据量处理时,生成器表达式的优势就体现出来了,因为它的内存使用方式更好,效率更高,它并不创建一个列表,只是返回一个生成器。

    而生成器表达式就和列表推导式差不多,就是将列表推导式的中括号换成小括号,这就是生成器表达式。

  生成器 表达式:生成器=(返回结构 执行对象  if判断条件)

# a=(i for i in range(30) if i%3==0)
# for i in a:
#     print(i)

面试题:

# def aa(n,i):
#     return n+i
# def bb():
#     yield from range(4)
# b=bb()
# for n in [1,10,5]:
#     b=(aa(n,i) for i in b)
# print(list(b))     [15,16,17,18]
# 
# 
# def aa(n,i):
#     return n+i
# def bb():
#     yield from range(4)
# b=bb()
# for n in [1,10,5]:
#     g=(aa(n,i) for i in b)
# print(list(g))    [5,6,7,8]

注意:这两个执行结果不同

  在这里的列表元素中的元素有几个,就会调用几次,只有在调用的时候值才会起作用,所以只用最后一个元素的值才能起作用。

原因:如果变量名是执行的对象,那么没执行一次,就会叠加一次

  而 变量名不是执行的对像,没执行一次就会从头开始执行进行下次执行,因此两次执行的结果不同

 根据已有的条件,将此条件用最简化的格式创建成一个新的你需要的列表形式,就叫做列表解析。

  列表解析是Python迭代机制的一种应用,它常用于实现创建新的列表,因此用在[]中。将成立的结果写在左边,不需要不成立的结果。

三 其他内容

 1 字典推导式:主要是用于在字典,将一些简单的代码更简单化。

d={'k1':1,'k2':2}
print({d[i]:i for i in d })

 2 集合推导式:和列表推导式功能差不多,但是他可以去掉元素的重复。

注意1 :尽量用推导式简化代码,怎强代码的可读性

注意2:如果推导式过于复杂,就不要用推到式,还是用普通的python代码就好。

三元表达式

  三元表达式就是可以将一些简单的if判断求值得方法再一次的简介化。会更好更简单的记住那个方法。

  三元表达式的公式是:

                           为真时的结果 if 判定条件 else 为假时的结果结果为错的执行

             结果正确的执行

   还可以求出函数的大小值如图

 

推荐阅读