浅谈Python闭包
闭包是在其词法上下文中引用了自由变量的函数。
通俗地说,就是函数嵌套(后续称之为外层函数)另外一个函数(后续称之为内层函数),在内层函数中,引用外层函数的变量,每次对内层函数的调用,外层函数变量的值都会进行保持。
用个简单的例子来说明,使用闭包实现一个函数,求所有传入的数字的平均值。
def averager():
"""
闭包实现求平均值的例子
每次传入一个数字,返回所有传入的数字的平均值
:return:
"""
count = 0
total = 0.0 def _averager(value):
nonlocal total, count
total += value
count += 1
average = total/count
return average return _averager # 调用外层函数averager,得到内层函数_averager的对象,赋值给avg
# 此时闭包形成,外层函数的变量total, count, average会被保持
avg = averager()
# 每次调用内层函数avg时,外层函数变量的值都会被记住
# 第一次调用,外层函数的变量count=1, total=10.0, average=10.0
print(avg(10))
# 10.0
# 第二次调用,外层函数变量的值不会重置,仍然保持上次调用的结果
# 此时 count=2, total=30.0, average=15.0
print(avg(20))
# 15.0
# 第三次调用,外层函数变量的值仍然会保持上次调用的结果
# 此时 count=3, total=36.0, average=12.0
print(avg(6))
# 12.0
上面的例子中,最重要的部分在调用外层函数averager时,需要返回内层函数的对象_averager
,注意这里的return _averager
没有括号,并不是调用内层函数,而是返回内层函数的对象。
avg_cls = Averager()
当调用外层函数,返回内层函数对象时,即形成闭包。
avg(10)
每次对内层函数的调用,外层函数中的变量的值,都会被记住,即保持上次调用的结果。
如果不容易理解,可以用类实例实现类似上面闭包的功能,实际执行中,因为类实例self的参与,运行速度要略慢于闭包的实现。
# 以类实现类似上面闭包的功能
class Averager: def __init__(self):
self.count = 0
self.total = 0.0 def __call__(self, value):
self.total += value
self.count += 1
average = self.total/self.count
return average avg_cls = Averager() print(avg_cls(10))
# 10.0
print(avg_cls(20))
# 15.0
print(avg_cls(6))
# 12.0
上面这个使用类实现的例子中,变量count和total,都保存在类实例avg_cls中,每次对类实例的调用,都会调用__call__
方法计算平均值,因为是同一个实例,所以count和total的值都会存储在实例中。
闭包也是类似的效果,变量count和total也是存储在外层函数的上下文中,所以每次对内层函数调用,外层函数的变量不会被销毁,而是一直保持初始值(未调用内层函数时)或上次调用的结果(每次调用内层函数后,对count和total的修改都会被存储)。
浅谈Python闭包的更多相关文章
- 浅谈python闭包及装饰器
1. 什么是闭包: 闭包 是指有权访问另一个函数作用域中变量的函数,创建闭包的最常见的方式就是在一个函数内创建另一个函数,通过另一个函数访问这个函数的局部变量,利用闭包可以突破作用链域,将函数内部的变 ...
- 开发技术--浅谈Python函数
开发|浅谈Python函数 函数在实际使用中有很多不一样的小九九,我将从最基础的函数内容,延伸出函数的高级用法.此文非科普片~~ 前言 目前所有的文章思想格式都是:知识+情感. 知识:对于所有的知识点 ...
- 浅谈Python时间模块
浅谈Python时间模块 今天简单总结了一下Python处理时间和日期方面的模块,主要就是datetime.time.calendar三个模块的使用.希望这篇文章对于学习Python的朋友们有所帮助 ...
- 浅谈Python在信息学竞赛中的运用及Python的基本用法
浅谈Python在信息学竞赛中的运用及Python的基本用法 前言 众所周知,Python是一种非常实用的语言.但是由于其运算时的低效和解释型编译,在信息学竞赛中并不用于完成算法程序.但正如LRJ在& ...
- 浅谈python字符串存储形式
http://blog.csdn.net/zhonghuan1992 钟桓 2014年8月31日 浅谈python字符串存储形式 记录一下自己今的天发现疑问而且给出自己现有知识有的回答. 长话短说,用 ...
- 开发技术--浅谈python数据类型
开发|浅谈python数据类型 在回顾Python基础的时候,遇到最大的问题就是内容很多,而我的目的是回顾自己之前学习的内容,进行相应的总结,所以我就不玩基础了,很多在我实际生活中使用的东西,我会在文 ...
- 开发技术--浅谈python基础知识
开发|浅谈python基础知识 最近复习一些基础内容,故将Python的基础进行了总结.注意:这篇文章只列出来我觉得重点,并且需要记忆的知识. 前言 目前所有的文章思想格式都是:知识+情感. 知识:对 ...
- [转]浅谈Python web框架
说到web framework,Ruby的世界Rails一统江湖,而Python则是一个百花齐放的世界,各种micro-framework.framework不可胜数,不完全列表见:http://wi ...
- 浅谈Python Web的五大框架
说到Web Framework,Ruby的世界Rails一统江湖,而Python则是一个百花齐放的世界.各种micro-framework.framework不可胜数. 尽管还有一大脚本语言PHP也有 ...
随机推荐
- js异步回调
简单理解:js是单线程的,Ajax请求远程数据.IO等会很耗时,引起堵塞可能会引起反应时间太长页面失去反应. 回调:A函数作为一个参数传给B函数,执行完B后再执行A: 同步回调: function A ...
- 常见IP端口
21端口:21端口主要用于FTP(File Transfer Protocol,文件传输协议)服务. 23端口:23端口主要用于Telnet(远程登录)服务,是Internet上普遍采用的登录和仿真程 ...
- 猜字游戏java
一.实践目的 1.掌握基本输入输出. 2.掌握方法定义与调用,理解参数传递方式. 3.掌握数组的声明.定义与初始化,数组的处理. 4.掌握数组作为方法参数和返回值. 二.实践要求 利用方法.数组.基本 ...
- Docker attach
Description Attach local standard input, output, and error streams to a running container Usage dock ...
- CentOS 离线安装Gitlab-ce
1. 上gtilab的官网,找了一下安装说明.. 首先安装 依赖的包 sudo yum install -y curl policycoreutils-python openssh-server cr ...
- Excel 使用AutoFill提示“类Range的AutoFill方法无效”
今天遇到一个神奇的问题,之前一直使用很好的代码突然报错:“类Range的AutoFill方法无效”,在网上搜索了一番,感觉没有一个与我遇到的情况相同的.debug,查看一下代码,发现程序里,AutoF ...
- 好文章系列C/C++——图说C++对象模型:对象内存布局详解
注:收藏好文章,得出自己的笔记,以查漏补缺! ------>原文链接:http://blog.jobbole.com/101583/ 前言 本文可加深对C++对象的内存布局.虚表指针.虚 ...
- Nginx PRECONTENT try_files指令
L:61 try_fiels指令 syntax : try_files file ... uri;=code //可以是多个文件 context : server,location; locatio ...
- pgm14
这部分讨论在有数据缺失情况下的 learning 问题,这里仍然假定了图结构是已知的. 首先需要讨论的是为什么会缺失,很多情况下缺失并不是“随机”的:有的缺失是人为的,那么某些情况下缺失的可以直接补上 ...
- BZOJ3750[POI2015]Pieczęć——链表
题目描述 一张n*m的方格纸,有些格子需要印成黑色,剩下的格子需要保留白色. 你有一个a*b的印章,有些格子是凸起(会沾上墨水)的.你需要判断能否用这个印章印出纸上的图案.印的过程中需要满足以下要求: ...