-
高级编程:验证函数接收参数类型(装饰器)
2019-01-14 19:54:27在编程中,如对函数的接收类型,有要求,比如: def add(x, y): return x + y if __name__ == '__main__': x = add(2,3) print("x=",x) 我们一看,就知道,这个出现:TypeError。 那么在编程...在编程中,如对函数的接收类型,有要求,比如:
def add(x, y): return x + y if __name__ == '__main__': x = add(2,3) print("x=",x)
我们一看,就知道,这个出现:TypeError。
那么在编程时,为了使用接收的参数的正确。我们可以使用python中的装饰器。
构建一个装饰器:
def requires_ints(decorated): def inner(*args, **kwargs): kwarg_values = [i for i in kwargs.values()] for arg in list(args) + kwarg_values: if not isinstance(arg, int): raise TypeError("参数中存在不是Int类型的:", decorated.__name__) return decorated(*args, **kwargs) return inner
测试方法:
@requires_ints def add(x, y): return x + y if __name__ == '__main__': # print(help(add)) x = add(2,3) print("x=",x)
输出过程:
完整代码:
# -*- coding: utf8 -*- """ # __author__ = "Tom枫明" # HomePage: https://blog.csdn.net/fm345689 # Python -V: Python 3.6.1 """ """ 装饰器:判断对应是否为一个Int类型 """ def requires_ints(decorated): def inner(*args, **kwargs): kwarg_values = [i for i in kwargs.values()] for arg in list(args) + kwarg_values: if not isinstance(arg, int): raise TypeError("参数中存在不是Int类型的:", decorated.__name__) return decorated(*args, **kwargs) return inner @requires_ints def add(x, y): return x + y if __name__ == '__main__': # print(help(add)) x = add(2,3.0) print("x=",x)
-
python中的装饰器,函数带参数的装饰器,带类参数的装饰器
2017-12-22 13:26:43其实,python 中的装饰器本质上就是一个函数,这个函数接收其他的函数作为参数,并将其以一个全新的修改后的函数替换它 关于装饰器的知识是python面试中比较常见的,对于装饰器的理解可以看这篇文章:理解Python中的...其实,python 中的装饰器本质上就是一个函数,这个函数接收其他的函数作为参数,并将其以一个全新的修改后的函数替换它
关于装饰器的知识是python面试中比较常见的,对于装饰器的理解可以看这篇文章:理解Python中的装饰器,理解之后,再手写一遍下面的8种装饰器加深理解以后使用就更轻松多了!1.最简单的函数
def myfunc() print "i am a function" myfunc()
2.初步了解装饰函数的调用结构
在函数执行前和执行后分别计时,打印函数运行消耗的时间
import datetime import time def out(fun): start = datetime.datetime.now() fun() end = datetime.datetime.now() print (end-start) return fun def inner(): time.sleep(1) print ("i am inner func") myfunc = out myfunc(inner)
3.尝试引用@语法糖来调用装饰函数
import datetime,time def out(func): start =datetime.datetime.now() func() end = datetime.datetime.now() print(end-start) return func @out def myfunc(): time.sleep(1) print("zhangkun inner")
4.使用内嵌的包装函数
使用内嵌包装函数来确保每次新函数都被调用,内嵌包装函数的形参和返回值与原函数相同,装饰函数返回内嵌包装函数对象
import datetime,time def out(func): def inner(): start = datetime.datetime.now() func() end = datetime.datetime.now() print(end-start) print("out and inner") return inner @out def myfunc(): time.sleep(1) print("zhangkun") myfunc()
5.对带参数的函数使用装饰器
内嵌包装函数的形参和返回值与原函数相同,装饰函数返回内嵌包装函数对象
import datetime,time def out(func): def inner(*args): start = datetime.datetime.now() func(*args) end = datetime.datetime.now() print(end-start) print("out and inner") return inner @out def myfunc(*args): time.sleep(1) print("args is{}".format(args)) myfunc("lalalal")
6.给装饰器参数
和上一示例相比在外层多了一层包装
#coding:utf-8 def outermost(*args): def out(func): print ("装饰器参数{}".format(args)) def inner(*args): print("innet start") func(*args) print ("inner end") return inner return out @outermost(666) def myfun(*args): print ("试试装饰器和函数都带参数的情况,被装饰的函数参数{}".format(args)) myfun("zhangkun")
7.带类参数的装饰器
class locker: def __init__(self): print("locker.__init__() should be not called") @staticmethod def acquire(): print("locker.acquire() static method be called") @staticmethod def release(): print("locker.release() static method be called") def outermost(cls): def out(func): def inner(): cls.acquire() func() cls.release() return inner return out @outermost(locker) def myfunc(): print("myfunc called") myfunc()
8.对一个函数应用多个装饰器
class mylocker: def __init__(self): print("mylocker.__init__() called.") @staticmethod def acquire(): print("mylocker.acquire() called.") @staticmethod def unlock(): print(" mylocker.unlock() called.") class lockerex(mylocker): @staticmethod def acquire(): print("lockerex.acquire() called.") @staticmethod def unlock(): print(" lockerex.unlock() called.") def lockhelper(cls): def _deco(func): def __deco2(*args, **kwargs): print("before %s called." % func.__name__) cls.acquire() try: return func(*args, **kwargs) finally: cls.unlock() return __deco2 return _deco class example: @lockhelper(mylocker) @lockhelper(lockerex) def myfunc2(self, a, b): print(" myfunc2() called.") print(a+b) a = example() a.myfunc2(1,2)
9.作为一个类
虽然装饰器几乎总是可以用函数实现,但是在某些情况下,使用用户自定义的类可能会更好,如果装饰器需要复杂的参数化或者依赖特定状态,那么这种说法往往是对的
非参数化装饰器用作类的通用模式如下class DerocatorAsClass: def __init__(self,funcation): self.funcation = funcation def __call__(self, *args, **kwargs): # 调用函数之前,做点什么 result = self.funcation(*args,**kwargs) # 在调用之后做点什么并且返回结果 return result
-
python装饰器函数-python 装饰器 函数被装饰+函数执行
2020-11-01 12:49:41func1.py 文件1、执行到@w12、被装饰函数作为装饰器参数 w1(func=f1())3、w1 函数执行有返回值,得用变量接收,变量名为f1 合适"""def w1(func):def inner():print('...验证权限...')func()return ..."""
func1.py 文件
1、执行到@w1
2、被装饰函数作为装饰器参数 w1(func=f1())
3、w1 函数执行有返回值,得用变量接收,变量名为f1 合适
"""
def w1(func):
def inner():
print('...验证权限...')
func()
return inner
@w1
def f1():
print('f1 called')
===================================================
"""
func2.py 文件
1、执行到@w1
2、被装饰函数作为装饰器参数 w1(func=f1())
3、w1 函数执行有返回值,得用变量接收,变量名为f1 合适
"""
def w1(func):
def inner():
print('...验证权限...')
func()
return inner
@w1
def f1():
print('f1 called')
f1()
"""
执行f1() 实际执行的是谁?-->是inner() 函数
为什么?-->步骤3 w1 函数返回值赋值给了f1
那实际是什么赋值给f1 变量了?-->是inner() 函数
现在执行f1() 当然执行的是inner() 函数
在执行inner() 函数的过程中有个func() 这个是什么?-->是w1 函数的参数
那这个函数实际执行的是谁?-->步骤2 有说明,实际指向的是被装饰的函数f1
"""
-
无参装饰器函数和带参装饰器函数
2016-10-07 15:41:26一、无参装饰器函数 Python的 decorator (装饰器) 本质上就是一个高阶函数,它接收一个函数作为参数,然后,返回一个新函数。 使用 decorator 用Python提供的 @ 语法,这样可以避免手动编写 f = decorate(f) 这样...一、无参装饰器函数
Python的 decorator (装饰器) 本质上就是一个高阶函数,它接收一个函数作为参数,然后,返回一个新函数。
使用 decorator 用Python提供的 @ 语法,这样可以避免手动编写 f = decorate(f) 这样的代码。
例1:
结果:#!/usr/bin/env python #coding=utf-8 #装饰器函数 def log(f): def fn(n): print 'call', f.__name__ + '()' return f(n) return fn #阶乘函数 @log def factorial(n): return reduce(lambda x,y : x*y, range(1,n+1)) print factorial(5)
对于参数只有一个的函数,@log工作的很好,但是当参数不是一个的函数,调用将报错:例2:
结果:#加法函数 @log def add(x, y): return x+y print add(1+2)
因为add()函数需要传入两个参数,但是@log写死了只含一个参数的返回函数。
所以要让 @log 自适应任何参数定义的函数,可以利用python的*arg 和 **kw,保证任意个数的参数能正常调用。
例3:
结果:#!/usr/bin/env python #coding=utf-8 #装饰器函数 def log(f): def fn(*args, **kw): print 'call', f.__name__ + '()' return f(*args, **kw) return fn #阶乘函数 @log def factorial(n): return reduce(lambda x,y : x*y, range(1,n+1)) #加法函数 @log def add(x, y): return x+y print add(1, 2) print factorial(5)
二、带参数的装饰器函数
需求来了:
如果有的函数非常重要,希望打印出'[INFO] call xxx()...',有的函数不太重要,希望打印出'[DEBUG] call xxx()...',这时,
log函数本身就需要传入'INFO'或'DEBUG'这样的参数,类似这样:
@log('DEBUG') def my_func(): pass
翻译成高阶函数相当于:
my_func = log('DEBUG')(my_func)
或者:
又相当于:log_decorator = log('DEBUG') my_func = log_decorator(my_func)
log_decorator = log('DEBUG') @log_decorator def my_func(): pass
估计看明白了。带参数的装饰器函数其实就是在原来的基础上添加外层函数,又返回内层的装饰器函数而已,也是很简单的。
总结:带参数的log函数首先返回一个decorator函数,再让这个函数接收decorator函数接收my_func并返回函数。代码如下:
结果:def log(prefix): def log_decorator(f): def wrapper(*args, **kw): print '[%s] %s()...' % (prefix, f.__name__) return f(*args, **kw) return wrapper return log_decorator @log('DEBUG') def test(): pass print test()
无参装饰器函数和有参的装饰器函数就基本上告一段落。
-
带参数的装饰器练习:确保函数接收到的参数为规定类型
2020-01-04 22:31:51题目要求: 代码: 运行结果: -
带参数的装饰器练习:确保函数接收到的参数与要求的对应。
2019-12-29 20:15:251.题目: 2.代码: -
python基础装饰器及能接收参数的装饰器
2019-05-11 23:46:29北京今天天儿不错,在家写点... 使用系统内置的warps装饰器能够使被装饰的函数保留他原始的信息, 直观一点就是在你print(func.__name__)的时候这个函数的名字仍然是func而不是new_func. """ @warps def new... -
第7章:函数装饰器和闭包-实现简单装饰器和参数化装饰器
2020-07-29 15:28:50装饰器接收被装饰的函数 def wrapper(*args, **kwargs): # 2. wrapper 接收被装饰函数的参数,然后将参数传给被装饰的函数: print(f'wrapper() 接收到位置参数{args}, 关键字参数{kwargs}') start_ti = time.... -
python 类装饰器如何接收request参数
2018-07-30 10:09:43我们在django中想要给类加上装饰器, 又想要用到被装饰函数的request参数 怎么办 ~ 我这是用来做权限校验的一个装饰器, 以此为例: class UserAuthentication(object): def __init__(self, func): self.... -
Python之带参数的装饰器练习:确保函数接收到的参数与要求的对应。
2020-01-03 17:21:391.题目: 2.代码: 3.结果: -
python函数装饰器参数 参数_python函数装饰器,迭代器,生成器+万能参数(动态参数)...
2020-12-04 21:12:18万能参数args:接收的是按照位置传参的值,然后组成一个元组**kwargs:接收的是按照关键字传参的值,然后组成一个字典传参的时候必须先按照位置传,然后是默认参数,然后再按照关键字传递(形参和实参中的都一样)在参数... -
装饰器练习:利用装饰器+isinstance实现确保函数接收到的每一个参数都是整数。
2019-12-29 20:08:511.题目: 2.代码: 补充: isinstance() 函数来判断一个对象是否是一个已知的类型,类似 type()。 举例: -
Python高阶函数与装饰器函数
2020-11-08 10:27:10Python高阶函数与装饰器函数 高阶函数 1、可以使用函数对象作为参数的函数 2、或可以将函数作为返回值的函数 3、函数对象:定义好的函数,使用函数名调用(不要加括号) #将函数作为参数的高阶函数,通过传入不同... -
装饰器练习:确保函数接收到的每一个参数都是整数;
2020-01-04 22:24:41题目要求: 代码: 运行结果: -
python中高阶函数和装饰器_Python高阶函数与装饰器函数的深入讲解
2020-12-11 08:08:30本文主要介绍的是Python高阶函数与装饰器函数的相关内容,分享给大家,下面话不多说了,来一起看看详细的介绍吧高阶函数1、可以使用函数对象作为参数的函数 2、或可以将函数作为返回值的函数 3、函数对象:定义好的... -
Python中使用函数或类去编写装饰器 及 如何给装饰器添加参数
2019-07-25 21:18:19装饰器是接收函数作为参数,添加功能后返回一个新函数的函数(类),装饰器既可以通过函数去实现,也可以通过类去实现。 Python中通过 @ 使用装饰器 装饰器模式就是通过实现一个装饰器,在不修改原来函数的情况下就... -
Python高阶函数与装饰器函数的深入讲解
2021-01-19 23:34:43本文主要介绍的是Python高阶函数与装饰器函数的相关内容,分享给大家,下面话不多说了,来一起看看详细的介绍吧 高阶函数 1、可以使用函数对象作为参数的函数 2、或可以将函数作为返回值的函数 3、函数对象:定义... -
Python装饰器练习,判断函数参数类型
2019-01-23 22:17:43当装饰器为@required_types(int,float)确保函数接收到的 每一个参数都是int或者float类型; # 2). 当装饰器为@required_types(list)确保函数接收到的每一个 参数都是list类型; # 3). 当装饰器为@required_... -
函数装饰器
2019-06-07 19:12:00对于某个函数,如果希望在不改变函数代码的前提下,为该函数增加额外的功能,那么可以使用装饰器来装饰该函数。...为了让内函数接收任意类型的参数,将内函数的形参定义为(*args, **kwargs)。在函数中首选完成为... -
python高阶函数讲解_Python高阶函数与装饰器函数的深入讲解
2021-01-11 22:45:27本文主要介绍的是Python高阶函数与装饰器函数的相关内容,分享给大家,下面话不多说了,来一起看看详细的介绍吧高阶函数1、可以使用函数对象作为参数的函数2、或可以将函数作为返回值的函数3、函数对象:定义好的... -
高阶函数与装饰器函数python
2020-11-23 22:59:49高阶函数是在Python中一个非常有用的功能函数,所谓高阶函数就是一个函数可以用来接收另一个函数作为参数,这样的函数叫做高阶函数。 map() map()是 Python 内置的高阶函数,它接收一个函数function 和一个 list,并... -
python函数参数生成器_python函数装饰器,迭代器,生成器+万能参数(动态参数)...
2020-12-08 13:38:27万能参数args:接收的是按照位置传参的值,然后组成一个元组**kwargs:接收的是按照关键字传参的值,然后组成一个字典传参的时候必须先按照位置传,然后是默认参数,然后再按照关键字传递(形参和实参中的都一样)在参数... -
Python: 无参数的函数装饰器
2014-04-02 20:34:00写带参数的函数装饰器最纠结的是需要包好多层,最外层是接收参数的函数,它返回一个接收函数的的函数。但这样有个问题是,最终包装出来的装饰器必须加()调用一下,即使没有参数也需要这样做,因为调用这个最外层函数... -
python装饰器详解 带参数-python中的装饰器详解
2020-11-11 14:04:56在了解装饰器的之前一定要先了解函数作为参数传递, 什么是函数内嵌,请参考我之前写的博客函数简介因为在python里面,函数也是对象,也可以作为参数进行传递.python装饰器本质也是一种特殊函数,它接收的参数是函数对象,... -
python函数装饰器,迭代器,生成器+万能参数(动态参数)
2019-09-24 08:33:49万能参数 args:接收的是按照位置传参的值,然后组成一个元组 **kwargs:接收的是按照关键字传参的值,然后组成一个字典 传参的时候必须先按照位置传,然后是默认参数,然后再按照关键字传递(形参和实参中... -
Python之装饰器:编写... 确保函数接收到的每一个参数都是整数; 2). 如果参数不是整形数, 打印 TypeError:
2020-01-03 17:17:231.题目: 2.代码: 3.输出: 补充: isinstance() 函数来判断一个对象是否是一个已知的类型,类似 type()。 举例: -
python中高阶函数和装饰器_python 高阶函数与装饰器
2020-12-11 08:08:27函数接收的参数是一个函数名2.函数的返回值是一个函数名以上两者满足任意一个,就是高阶函数装饰器定义本质就是函数,功能是为其他函数添加新功能装饰器的原则1.不修改被装饰函数的源代码(开放封闭原则)2.为被装饰... -
python 函数装饰器
2018-04-18 17:47:12在学习装饰器的时候,对带参数的装饰器有些不太理解 通过例子有了一点想法记录下来,后续遇到问题的时候回顾反思一下吧问题:打印出函数运行的时间,可以传入参数 选择打印s 或者 ms代码:import time def ...
-
牛牛量化策略交易
-
小知识点:null, undefined, NaN, Infinity的值是否相等或全等
-
FFmpeg4.3系列之16:WebRTC之小白入门与视频聊天的实战
-
MySQL 高可用工具 DRBD 实战部署详解
-
Xyplayer X3.9.3正式版.rar
-
linux云服务器上使用免费版natapp进行内网穿透
-
FPGA入门学习路线.pdf
-
用 PyQt5 制作动态钟表
-
各种显示器色域测试软件和计算显示器色域值软件和表格
-
只需要几秒 超强win10关闭自动更新工具.rar
-
使用vue搭建微信H5公众号项目
-
360手机卫士模块结构图(wainshine制作)[1].jpeg
-
OC.Gen-X.2.9.2.dmg
-
摄影测量之空间后方交会程序.zip
-
深度学习自学第四周:近几年的经典神经网络结构
-
Day51(泛型)
-
LVS + Keepalived 实现 MySQL 负载均衡与高可用
-
Mysql数据库面试直通车
-
从底层了解volatile的规则
-
2021年 系统分析师 系列课