python之路——第二块(装饰器、生成器、迭代器)
装饰器
def deco(count): def func(num): if num < 10: count(num) else: exit() return func @deco def count(num): a = 0 for i in range(num): a += i print(a) count(11)
注:deco(count)和下面的count(num)中的count只是一个形参,count可以用任何变量名替换,但是num是一定要有,因此传入的实参是被装饰函数,被装饰函数有num形参。
总结:1、装饰器没有修改被装饰函数的源代码和调用方式
2、用到了高阶函数,把被装饰函数函数名当做实数传入装饰器第一级函数;装饰器第二级函数包含被装饰函数以及要加的新功能,然后将第二级函数的内存地址返回给第一级函数。这样就能达到装饰的效果。
3、用到了嵌套函数,第一级函数嵌套第二级函数。
生成器:一边循环一边计算的机制,节省内存空间;只有在调用这个生成器时,才会生成想应的数据。
首先看一个列表生产式
a = [i*2 for i in range(10)] #列表生产式 print(a) #直接打印a列表的所有结果
但是如果range()里面是10000的时候,就会占用电脑大量内存,我们需要的仅仅是其中一个数据。此时可以用生成器
b = (i*2 for i in range(10)) #生成器 print(b) #打印的是内存地址
此时,b就是生成器,打印b显示的是内存地址,可用_next_方法
print(b.__next__()) #0 print(b.__next__()) #2 print(b.__next__()) #4
除了这种列表生产器,还可以把函数改装生成器,比如下面一个斐波那契函数
def fei(max): #斐波那契额函数 a,b,n = 0,1,0 while n < max: print(b) a,b = b,a+b n += 1
调用这个函数,输出的是整个斐波那契列表,但是可以把print(b)改成yield b的方法,把函数变成生成器。
def feib(max): a,b,n = 0,1,0 while n < max: yield b #将print 改为 yield 变成斐波那契生成器 a,b = b,a+b n += 1 f = feib(10) print(f.__next__()) #1 print(f.__next__()) #1 print(f.__next__()) #2
可以用for的方法,来输出生产器的所有结果
for i in fei(10): print(i)
输出的结果和
f = fei(10)
的结果一样
可迭代对象:可以直接作用于for
循环的对象统称为可迭代对象:Iterable
迭代器:可以被_next_()
函数调用并不断返回下一个值的对象称为迭代器:Iterator
1、可以使用isinstance()
判断一个对象是否是Iterable
对象
2、集合数据类型,如list
、tuple
、dict
、set
、str
等可以使用for循环,但是不具有_next_()方法,使用只属于可迭代对象,不属于迭代器
所以,生成器属于迭代器,也属于可迭代对象,但是迭代器不一定是生成器。