python之路4:各种器

  1. 装饰器
  2. 生成器
  3. 迭代器

一、装饰器

装饰器是函数,官方叫语法糖,只不过该函数可以具有特殊的含义,装饰器用来装饰函数或类,使用装饰器可以在函数执行前和执行后添加相应操作。

语法:  

def wrapper(func):
    def result():
        print(‘before‘)
        func()
        print(‘after‘)

    return result

@wrapper
def foo():
    print(‘foo‘)

实例:

#!/usr/bin/env python
# -*- coding:utf-8 -*-
# __author__ = ‘lvlibing‘

import time

def timer(func): #timer(test1)  func = test1
    def deco(*args,**kwargs):
        start_time = time.time()
        func(*args,**kwargs) #run test1()
        stop_time = time.time()
        print(‘the func run time is %s‘ %(start_time - stop_time))
    return deco

@timer # test1 = timer(test1)
def test1():
    time.sleep(1)
    print(‘in the test1‘)

@timer # test2 =timer(test2) = deco test2(name) = deco(name)
def test2(name,age):
    print(‘test2:‘,name,age)

test1()
test2(‘lv‘,22)

  

  

二、生成器

一边循环一边计算的机制,称为生成器:generator。

要创建一个generator,有很多种方法。第一种方法很简单,只要把一个列表生成式的[]改成(),就创建了一个generator:


1

2

3

4

5

6

>>> L = [x * for in range(10)]

>>> L

[0149162536496481]

>>> g = (x * for in range(10))

>>> g

<generator object <genexpr> at 0x1022ef630>

创建Lg的区别仅在于最外层的[]()L是一个list,而g是一个generator。

我们可以直接打印出list的每一个元素,但我们怎么打印出generator的每一个元素呢?

如果要一个一个打印出来,可以通过next()函数获得generator的下一个返回值。

如果一个函数定义中包含yield关键字,那么这个函数就不再是一个普通函数,而是一个generator。

generator和函数的执行流程不一样。函数是顺序执行,遇到return语句或者最后一行函数语句就返回。而变成generator的函数,在每次调用next()的时候执行,遇到yield语句返回,再次执行时从上次返回的yield语句处继续执行。

#!/usr/bin/env python
# -*- coding:utf-8 -*-
# __author__ = ‘lvlibing‘

import time

"""
‘列表生成式‘
a = (x * x for x in range(100))
print(a)

for loop in a:
    print(loop)

print(a.__next__())
# print(a.__next__())
# print(a.__next__())
"""
#Fibonacci斐波那契数列
def fibnaci(max):
    n,a,b = 0,0,1
    while n < max:
        #print(b) #会执行return,获得done返回值
        yield b #函数定义中包含yield关键字,此时函数将变成一个生成器,不会执行return
    #tuple = (b,a+b)
    # a,b = tuple[0],tuple[1]
        a,b = b,a+b
        n += 1
    return ‘done‘

f=fibnaci(10)
print(f)
# print(f.__next__())
‘‘‘
for n in f:
    print(n)

‘‘‘
while True:
    try:
        t = next(f)
        print(‘f:‘,t)
    except StopIteration as e:
        print(‘Generator return value:‘, e.value)
        break

#生产消费者模型,协程(生成器并行运算)
def consumer(name):
    print(‘%s准备吃包子了‘%name)
    while True:
        baozhi = yield
        print(‘包子[%s]来了,被[%s]吃了‘ %(baozhi,name))

def producer(name):
    c1 = consumer(‘a‘)
    c2 = consumer(‘b‘)
    c1.__next__()
    c2.__next__()
    print(‘后厨开始准备做包子‘)
    for i in range(10):
        time.sleep(1)
        print(‘做了2个包子‘)
        c1.send(i)#send方法调用前面函数yiled
        c2.send(i)#send方法调用前面函数yiled

producer(‘lv‘)

  

 

三、迭代器

我们已经知道,可以直接作用于for循环的数据类型有以下几种:

一类是集合数据类型,如listtupledictsetstr等;

一类是generator,包括生成器和带yield的generator function。

这些可以直接作用于for循环的对象统称为可迭代对象:Iterable

可以使用isinstance()判断一个对象是否是Iterable对象。

可以被next()函数调用并不断返回下一个值的对象称为迭代器:Iterator。

生成器都是Iterator对象,但listdictstr虽然是Iterable,却不是Iterator

listdictstrIterable变成Iterator可以使用iter()函数。

你可能会问,为什么listdictstr等数据类型不是Iterator

这是因为Python的Iterator对象表示的是一个数据流,Iterator对象可以被next()函数调用并不断返回下一个数据,直到没有数据时抛出StopIteration错误。可以把这个数据流看做是一个有序序列,但我们却不能提前知道序列的长度,只能不断通过next()函数实现按需计算下一个数据,所以Iterator的计算是惰性的,只有在需要返回下一个数据时它才会计算。

Iterator甚至可以表示一个无限大的数据流,例如全体自然数。而使用list是永远不可能存储全体自然数的。

小结

凡是可作用于for循环的对象都是Iterable类型;

凡是可作用于next()函数的对象都是Iterator类型,它们表示一个惰性计算的序列;

集合数据类型如listdictstr等是Iterable但不是Iterator,不过可以通过iter()函数获得一个Iterator对象。

#!/usr/bin/env python
# -*- coding:utf-8 -*-
# __author__ = ‘lvlibing‘

from collections import Iterable
from collections import Iterator

print(isinstance((), Iterable))#T
print(isinstance([], Iterable))#T
print(isinstance({}, Iterable))#T

print(isinstance({}, Iterator))#F
print(isinstance([], Iterator))#F
print(isinstance(iter([]), Iterator))#T
print(isinstance(iter({}), Iterator))#T

‘‘‘
for x in [1,3,5,7,9]:
    pass
等同
it = iter([1,3,5,7,9])
while True:
    try:
        x = next(it)
    except StopIteration:
        break
‘‘‘

  

时间: 2024-10-12 13:16:15

python之路4:各种器的相关文章

Python之路23-迭代器

#迭代器 #可直接作用于for循环的数据类型 #一类是集合数据类型,list,tuple,dict,set,str #一类是generator,包括生成器和带yield的generator function #这些可以直接作用于for循环的对象统称为可迭代对象:Iterable #可以使用isinstance()判断一个对象是否是Iterable对象 from collections import Iterable print (isinstance("abc",Iterable))

Python不归路_装饰器(二)

装饰器上节回顾 装饰器主要是由高阶函数和嵌套函数组成的,它由有两大特性:1.不改变被装饰函数原代码:2.不改变被装饰函数调用方式 高阶函数主要有两大特性:1.被装饰函数作为高阶函数的参数:2.return函数 嵌套函数特性:在一个函数内,新定义一个函数 下面我们来看一段代码,给login_index()和login_mang()添加用户密码认证的功能的装饰器. user='gally' #定义用户名 password='123' #定义密码 def auth(func): #定义装饰器 被装饰函

Python不归路_装饰器(一)

装饰器 装饰器 什么是装饰器?给现有函数添加新功能的函数,不更改现有函数源代码,现有函数调用方式.装饰器是由高阶函数和嵌套函数组成. 概括上面这句话的意思:1.装饰器 - - - > 函数 : 2.不更改现有函数源代码 3.不更改现有函数调用方式 4.装饰器对于函数来说是透明的(不产生任何影响) 装饰器运用的情景:在生产环境中,业务不能中断时,要给某些大量调用函数填加新功能时. 高阶函数  怎么样的函数才是高阶函数 1.把函数名作为实参传递给另外一个函数 2.返回值中包括函数 下面我们来感受下高

python之路-11-装饰器

11.1装饰器的基本概念 装饰器定义:本质是函数,功能是装饰其它函数(就是为其他函数添加附加功能) 原则:1.不能修改被装饰的函数的源代码 不能修改被装饰的函数的调用方式 总结:装饰器对被装饰的函数是完全透明的(被装饰的函数不知道装饰器的存在,而装饰器可装饰函数来实现所需功能) 实现装饰器知识储备: 函数即"变量" 高阶函数 把一个函数名当做实参传给另外一个函数(在不修改被装饰函数源代码的情况下为其添加) 返回值中包含函数名(不修改函数的调用方式) 嵌套函数:在一个函数的函数体内用de

七日Python之路--第十二天(Django Web 开发指南)

<Django Web 开发指南>.貌似使用Django1.0版本,基本内容差不多,细读无妨.地址:http://www.jb51.net/books/76079.html (一)第一部分 入门 (1)内置数字工厂函数 int(12.34)会创建一个新的值为12的整数对象,而float(12)则会返回12.0. (2)其他序列操作符 连接(+),复制(*),以及检查是否是成员(in, not in) '**'.join('**')   或  '***%s***%d' % (str, int)

Python之路【第三篇】:Python基础(二)

Python之路[第三篇]:Python基础(二) 内置函数 一 详细见python文档,猛击这里 文件操作 操作文件时,一般需要经历如下步骤: 打开文件 操作文件 一.打开文件 1 文件句柄 = file('文件路径', '模式') 注:python中打开文件有两种方式,即:open(...) 和  file(...) ,本质上前者在内部会调用后者来进行文件操作,推荐使用 open. 打开文件时,需要指定文件路径和以何等方式打开文件,打开后,即可获取该文件句柄,日后通过此文件句柄对该文件操作.

Python之路【第十九篇】:爬虫

Python之路[第十九篇]:爬虫 网络爬虫(又被称为网页蜘蛛,网络机器人,在FOAF社区中间,更经常的称为网页追逐者),是一种按照一定的规则,自动地抓取万维网信息的程序或者脚本.另外一些不常使用的名字还有蚂蚁.自动索引.模拟程序或者蠕虫. Requests Python标准库中提供了:urllib.urllib2.httplib等模块以供Http请求,但是,它的 API 太渣了.它是为另一个时代.另一个互联网所创建的.它需要巨量的工作,甚至包括各种方法覆盖,来完成最简单的任务. import

Python之路【第八篇】:堡垒机实例以及数据库操作

Python之路[第八篇]:堡垒机实例以及数据库操作 堡垒机前戏 开发堡垒机之前,先来学习Python的paramiko模块,该模块机遇SSH用于连接远程服务器并执行相关操作 SSHClient 用于连接远程服务器并执行基本命令 基于用户名密码连接: + import paramiko transport = paramiko.Transport(('hostname', 22)) transport.connect(username='wupeiqi', password='123') ssh

Python之路_Day5

Python之路_Day5_课堂笔记 ---------------------------------------------------------------------------------------------------- 前期回顾: 一.python基础 二.基本数据类型 int str list tuple dict set 三.函数式编程 四.装饰器 1.将func当作参数传递给装饰器,并执行 2.将装饰器函数的返回值重新赋值给func ------------------

Python之路:堡垒机实例以及数据库操作

Python之路:堡垒机实例以及数据库操作 一.堡垒机前戏 开发堡垒机之前,先学习Python的paramiko模块,该模块基于SSH用于连接远程服务器并执行相关操作. SSHClient 用于连接远程服务器并执行基本命令 基于用户名密码连接: #!/usr/bin/env  python# --*--coding:utf-8 --*--import paramiko #创建SSH对象ssh = paramiko.SSHClient()# 允许连接不在know_hosts文件中的主机ssh.se