python-装饰器

理解函数

在python中,函数是一个函数对象,定义函数时,将这个函数对象赋值给了一个变量(函数名)

#理解函数,函数也是一个对象,定义函数时,将这个函数对象赋值给了一个变量(函数名)

def double(x):
    return x**2

print(double)
print(dir(double))

运行结果:

<function double at 0x7f8cccdd3040>
['__annotations__', '__call__', '__class__', '__closure__', '__code__', '__defaults__', '__delattr__', '__dict__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__get__', '__getattribute__', '__globals__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__kwdefaults__', '__le__', '__lt__', '__module__', '__name__', '__ne__', '__new__', '__qualname__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__']

函数是一个callable,可以调用

函数既可以作为其他函数的参数,也可以作为返回值

当函数作为其他函数的参数时,这个函数被称为回调函数

#函数可以做其他函数的参数
from math import pi
def circle(x):
    return pi*2*x

def are(x):
    return pi*x**2

#将函数作为参数
def cal_circle(f,x):
    return f(x)

#传入不同的函数名作为参数时,在内部进行调用
print(cal_circle(circle,3))
print(cal_circle(are,3))

运行结果:

18.84955592153876
28.274333882308138
函数作为返回值
# 如下函数的返回值是一个函数
def get_multiple_function(n):

    def multiple(x):
        return n*x
    return multiple
#这个地方并没有调用mutiple函数,而是返回了mutiple函数
double=get_multiple_function(2)
#double是一个function对象,可以callable
print(type(double))
print(double(3))

单步调试,可以看到,double是一个mutiple的函数
在这里插入图片描述

装饰器函数

装饰器是一个参数是函数,返回值也是函数的一个函数

def dec(f):
    pass

@dec
def double(x):
    return x*2


#等价于
double=dec(double)

一般装饰器都会返回一个函数
如下,有一个计算1000以内有多少个质数的函数:

def is_prime(num):
    if num<2:
        return False
    elif num==2:
        return True
    else:
        for i in range(2,num):
            if(num%i==0):
                return False
        return True

def prime_nums():
    for i in range(2,1000):
        if is_prime(i):
            print(i)

prime_nums()

需求:想要计算出,找出这些质数用的时间
可以在函数的开始和结束加上time
如下:


import time

def is_prime(num):
    if num<2:
        return False
    elif num==2:
        return True
    else:
        for i in range(2,num):
            if(num%i==0):
                return False
        return True

def prime_nums():
    begin=time.time()
    for i in range(2,1000):
        if is_prime(i):
            print(i)
    end=time.time()
    print("total time %f"%(end-begin))

prime_nums()

但是如果还有其他函数需要计算执行的时间,这样就重复添加time
可以将计算时间的代码单独提取出来,将其他函数作为参数

import time

def is_prime(num):
    if num<2:
        return False
    elif num==2:
        return True
    else:
        for i in range(2,num):
            if(num%i==0):
                return False
        return True

def prime_nums():
    for i in range(2,1000):
        if is_prime(i):
            print(i)



def cal_time(f):
    begin=time.time()
    f()
    end=time.time()
    print("Total time %f"%(end-begin))
    
cal_time(prime_nums)

如果f有参数

import time

def is_prime(num):
    if num<2:
        return False
    elif num==2:
        return True
    else:
        for i in range(2,num):
            if(num%i==0):
                return False
        return True

def prime_nums(num):
    for i in range(2,num):
        if is_prime(i):
            print(i)



def cal_time(f,num):
    begin=time.time()
    f(num)
    end=time.time()
    print("Total time %f"%(end-begin))

cal_time(prime_nums,10000)

以上计算时间的函数可以改写成一个带有内部函数的函数

import time

def is_prime(num):
    if num<2:
        return False
    elif num==2:
        return True
    else:
        for i in range(2,num):
            if(num%i==0):
                return False
        return True

def prime_nums():
    for i in range(2,10000):
        if is_prime(i):
            print(i)



def cal_time(f):
    def wapper():
        begin=time.time()
        f()
        end=time.time()
        print("Total time is %f"%(end-begin))
    return wapper

#返回了wapper函数,并将其赋值给p
p=cal_time(prime_nums)
#使用p调用wapper
p()

cal_time是一个参数是函数,返回值也是函数的一个函数,以上调用比较麻烦,写成装饰器
等价于:

import time

def cal_time(f):
    def wapper():
        begin=time.time()
        f()
        end=time.time()
        print("Total time is %f"%(end-begin))
    return wapper

def is_prime(num):
    if num<2:
        return False
    elif num==2:
        return True
    else:
        for i in range(2,num):
            if(num%i==0):
                return False
        return True

@cal_time
def prime_nums():
    for i in range(2,10000):
        if is_prime(i):
            print(i)


prime_nums()
如果这个function需要返回值
import time

def cal_time(f):
    def wapper():
        begin=time.time()
        #定义一个变量,接受function的值,并将这个值再返回
        result=f()
        end=time.time()
        print("Total time is %f"%(end-begin))
        return result
    return wapper

def is_prime(num):
    if num<2:
        return False
    elif num==2:
        return True
    else:
        for i in range(2,num):
            if(num%i==0):
                return False
        return True

@cal_time
def prime_nums():
    count=0
    for i in range(2,10000):
        if is_prime(i):
            count+=1
    return count


result=prime_nums()
print(result)
如果这个function需要参数
import time

def cal_time(f):
    #传入参数,并将这个参数传入到function中
    def wapper(*args):
        begin=time.time()
        #定义一个变量,接受function的值,并将这个值再返回
        result=f(*args)
        end=time.time()
        print("Total time is %f"%(end-begin))
        return result
    return wapper

def is_prime(num):
    if num<2:
        return False
    elif num==2:
        return True
    else:
        for i in range(2,num):
            if(num%i==0):
                return False
        return True

@cal_time
def prime_nums(num):
    count=0
    for i in range(2,num):
        if is_prime(i):
            count+=1
    return count


result=prime_nums(100000)
print(result)
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值