python中函数总结之装饰器闭包详解


Posted in Python onJune 12, 2016

1、前言

函数也是一个对象,从而可以增加属性,使用句点来表示属性。

如果内部函数的定义包含了在外部函数中定义的对象的引用(外部对象可以是在外部函数之外),那么内部函数被称之为闭包。

2、装饰器

装饰器就是包装原来的函数,从而在不需要修改原来代码的基础之上,可以做更多的事情。

装饰器语法如下:

@deco2
@deco1
def func(arg1,arg2...):
  pass

这个表示了有两个装饰器的函数,那么表示的含义为:func = deco2(deco1(func))

无参装饰器语法如下:

@deco
def func():
  pass

表示的含义为func = deco(func)

有参装饰器语法如下:

@deco(deco_args)
def func():
  pass

表示的含义为:func = deco(deco_args)(func)

多个装饰器有的有参数有的没参数,语法如下:

@deco2(arg1,arg2)
@deco1
def func():
  pass

表示的含义为foo = deco2(arg1,arg2)deco1(func)

装饰器实际上就是函数,接受的也是函数对象。

在执行函数之前,可以运行预备代码,也可以在执行代码后做一些清理工作。

看见装饰器的时候,很可能在里面找到一些代码,它定义了某个函数,并在定义内的某处嵌入了对目标函数的调用或者至少一点引用。

3、装饰器作用

装饰器的作用如下:

引入日志;增加计时逻辑来检测性能;给函数加入了事物的能力

以下例子表示为引入了计时的逻辑来检测性能,如下:

#!/usr/bin/env python

from time import ctime,sleep

def tsfunc(func): #装饰器函数接受的是一个函数对象
  def wrappedFunc():
    print '[%s] %s() called' % (ctime(),func.__name__)
    return func() #在这里调用了函数对象,也就是表示装饰器是装饰了原来的函数,从而在原来函数的基础上进行了一些操作
  return wrappedFunc

@tsfunc #装饰器
def foo():
  pass

foo()
sleep(4)

for i in range(2):
  sleep(1)
  foo()

 执行结果如下:

[root@python 420]# python deco.py 
[Tue Apr 19 16:15:01 2016] foo() called
[Tue Apr 19 16:15:06 2016] foo() called
[Tue Apr 19 16:15:07 2016] foo() called

在装饰器函数中,增加了时间戳并且调用了目标函数,装饰器的返回值是一个包装了函数

4、闭包

如果在一个内部函数里,对在外部作用于(但不是全局作用域)的变量进行引用,那么内部函数被认为是闭包closure,定义在外部函数内的但由内部函数引用或者使用的变量称之为自由变量。

闭包的主要作用如下:

安装计算;隐藏状态;在函数对象和作用域中随意的切换。

回调就是函数,闭包也是函数,但是能携带一点额外的作用域。

#!/usr/bin/env python

def counter(start_at=0):
  count = [start_at]
  def incr():
    count[0] += 1
    return count[0]
  return incr

count= counter(5)
print count()
print count()

在上面的例子可以看到,函数内部的函数incr引用了外部的变量count,并且每次进行加一,从而这个变量count称之为自由变量。

以上这篇python中函数总结之装饰器闭包详解就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
python 参数列表中的self 显式不等于冗余
Dec 01 Python
动态创建类实例代码
Oct 07 Python
Python读取图片属性信息的实现方法
Sep 11 Python
python字符串,数值计算
Oct 05 Python
Python pyinotify日志监控系统处理日志的方法
Mar 08 Python
Python文件读写保存操作的示例代码
Sep 14 Python
python判断数字是否是超级素数幂
Sep 27 Python
kafka-python批量发送数据的实例
Dec 27 Python
pytorch如何冻结某层参数的实现
Jan 10 Python
TensorFlow:将ckpt文件固化成pb文件教程
Feb 11 Python
基于Python编写一个计算器程序,实现简单的加减乘除和取余二元运算
Aug 05 Python
Python调用C/C++的方法解析
Aug 05 Python
Python备份目录及目录下的全部内容的实现方法
Jun 12 #Python
深入理解python中的闭包和装饰器
Jun 12 #Python
Python编码爬坑指南(必看)
Jun 10 #Python
浅析Python中的for 循环
Jun 09 #Python
Python多层嵌套list的递归处理方法(推荐)
Jun 08 #Python
Python-嵌套列表list的全面解析
Jun 08 #Python
PYTHON压平嵌套列表的简单实现
Jun 08 #Python
You might like
php文件夹与文件目录操作函数介绍
2013/09/09 PHP
PHP中使用Imagick操作PSD文件实例
2015/01/26 PHP
PHP文件缓存类示例分享
2015/01/30 PHP
PHP封装的HttpClient类用法实例
2015/06/17 PHP
Nigma vs Alliance BO5 第三场2.14
2021/03/10 DOTA
JavaScript可否多线程? 深入理解JavaScript定时机制
2012/05/23 Javascript
在javascript中对于DOM的加强
2013/04/11 Javascript
jquery 获取dom固定元素 添加样式的简单实例
2014/02/04 Javascript
jQuery实现鼠标划过展示大图的方法
2015/03/09 Javascript
jQuery基于图层模仿五星星评价功能的方法
2015/05/07 Javascript
浅析angularJS中的ui-router和ng-grid模块
2016/05/20 Javascript
使用JS中的exec()方法构造正则表达式验证
2016/08/01 Javascript
Jquery循环截取字符串的方法(多出的字符串处理成"...")
2016/11/28 Javascript
JS常见创建类的方法小结【工厂方式,构造器方式,原型方式,联合方式等】
2017/04/01 Javascript
Vue自定义指令使用方法详解
2017/08/21 Javascript
Bootstrap 树控件使用经验分享(图文解说)
2017/11/06 Javascript
动态加载权限管理模块中的Vue组件
2018/01/16 Javascript
浅谈webpack-dev-server的配置和使用
2018/05/17 Javascript
在Vant的基础上封装下拉日期控件的代码示例
2018/12/05 Javascript
微信小程序用户拒绝授权的处理方法详解
2019/09/20 Javascript
JS实现分页导航效果
2020/02/19 Javascript
[00:18]天涯墨客三技能展示
2018/08/25 DOTA
浅谈flask截获所有访问及before/after_request修饰器
2018/01/18 Python
为什么选择python编程语言入门黑客攻防 给你几个理由!
2018/02/02 Python
python PyTorch参数初始化和Finetune
2018/02/11 Python
Python3批量生成带logo的二维码方法
2019/06/24 Python
python使用原始套接字发送二层包(链路层帧)的方法
2019/07/22 Python
python实现UDP协议下的文件传输
2020/03/20 Python
python开发前景如何
2020/06/11 Python
html5自带表单验证体验优化及提示气泡修改功能
2017/09/12 HTML / CSS
ASICS印度官方网站:日本专业运动品牌
2020/06/20 全球购物
大学学生个人总结
2015/02/15 职场文书
Pytest中conftest.py的用法
2021/06/27 Python
JavaScript最完整的深浅拷贝实现方式详解
2022/02/28 Javascript
90后经典动画片排行:《数码宝贝》第二,《小鲤鱼历险记》在榜
2022/03/18 日漫
浅谈Vue的computed计算属性
2022/03/21 Vue.js