前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >Python: yield用法的解析

Python: yield用法的解析

作者头像
Exploring
发布于 2022-09-20 06:07:06
发布于 2022-09-20 06:07:06
1.3K00
代码可运行
举报
运行总次数:0
代码可运行

文章背景: 在看别人写的Python代码时,有时会遇到yield这个生僻的关键字,影响了代码的阅读进度。因此,本文在查阅相关资料的基础上,对yield的用法进行了介绍。

1 yield关键字

yield在函数中的功能类似于return,不同的是yield每次返回结果之后函数并没有退出,而是 每次遇到yield关键字后返回相应结果,并保留函数当前的运行状态,等待下一次的调用。如果 一个函数需要多次循环执行一个动作,并且每次执行的结果都是需要的,这种场景很适合使用yield实现。

包含yield的函数成为一个生成器,生成器同时也是一个迭代器,支持通过next方法获取下一个值。

使用yield的好处是通过使用生成器,避免占用内存,提高运行效率。

2 代码示例

示例代码块如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
def foo():
    print("starting...")
    while True:
        result = yield 4
        print("result:", result)


test = foo()
print(next(test))
print("*"*20)
print(next(test))

运行结果:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
starting...
4
********************
result: None
4

代码分析

(1) 针对test = foo(),由于函数foo中存在yield关键字,所以函数foo内的代码一开始并不执行,而是得到一个生成器test(相当于一个对象)。

(2) 针对print(next(test))。由于调用了next方法,foo函数开始执行。先输出starting...,然后进入while循环。在循环内,遇到yield关键字。这里可以把yield想象成return。因此,foo函数返回4,并通过print函数输出。注意:这里并没有执行result的赋值操作。

(3) 针对print("*"*20)。程序输出20个星号。

(4)针对print(next(test))。这句代码是接着步骤(2)结束的地方开始执行,执行的是result的赋值操作。注意:由于在步骤(2)的时候,4已经return出去,并没有完成赋值操作。因此,现在给result赋的值是None。所以输出的结果是result: None。程序接着在While内继续执行,又一次碰到yield关键字,同样返回4,并通过print函数输出。

总结一下,带yield的函数是一个生成器,而不再是一般意义上的一个函数了,这个生成器有一个方法就是next方法,next就相当于“下一步”生成哪个数,这一次的next开始的地方是接着上一次的next停止的地方执行的,所以第二次调用next的时候,生成器并不会从foo函数最开始的地方执行,而是接着上一步停止的地方开始,然后遇到yield后,return出要生成的数,此步就结束。

3 两点补充

(1)除了next方法,yield得到的生成器还支持send方法。该方法可以向生成器传递参数。

代码块示例如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
def foo():
    print("starting...")
    while True:
        result = yield 4
        print("result:", result)


test = foo()
print(next(test))
print("*"*20)
print(test.send(7))

运行结果:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
starting...
4
********************
result: 7
4

针对最后一条语句print(test.send(7))send函数开始执行的时候,接着上一回next方法结束的地方,先完成赋值操作,将7赋值给变量result。然后执行next方法的功能。先输出结果result: 7。然后在While内继续执行,又一次碰到yield关键字,同样返回4,并通过print函数输出。

(2)对于yield得到的生成器,当调用方法next时,将获取生成器yield后边表达式的值;当执行完最后一次循环后,结束yield语句;此时,如果继续调用next方法,生成器会抛出StopIteration异常。

代码块示例如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
def func():
    for i in range(0, 2):
        yield i


f = func()
print(next(f))
print(next(f))
print(next(f))

运行结果:

当第三次调用next函数时,由于yield语句已经结束,因此, 程序抛出StopIteration异常。

参考资料:

[1] python中yield用法(https://blog.csdn.net/dcrmg/article/details/78128041

[2] python中yield的用法详解——最简单,最清晰的解释(https://blog.csdn.net/mieleizhi0522/article/details/82142856

[3] Python yield 使用浅析(https://www.runoob.com/w3cnote/python-yield-used-analysis.html

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2022-03-20,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 数据处理与编程实践 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
canvas扇形图、饼状图绘制
上一篇说过使用arc属性绘制一个完整的圆,这是绘制扇形是不是可以刷一下小聪明吧弧度修改一下,你会发现绘制的扇形想西瓜皮一样,只有初始弧度到结束弧度的一个简单连接,就行下面这个样子,这肯定不是我们想要扇形的样子哇
十月梦想
2018/08/29
3.8K0
canvas实现验证码
在通常的登录界面我们都可以看到验证码,验证码的作用是检测是不是人在操作,防止机器等非人操作,防止数据库被轻而易举的攻破。
ProsperLee
2018/10/24
8260
canvas实现验证码
Canvas 实现 progress 效果
本文介绍如何使用HTML5的Canvas特性实现一个进度条效果。通过创建一个圆形的绘制区域,并利用Canvas的API(如beginPath,arc,stroke,fill等)来控制进度条的绘制。同时,还演示了如何设置进度条的宽度和高度,以及如何在进度条中添加文本。最后,给出了一段测试代码,以展示该进度条的效果。
腾讯IVWEB团队
2017/03/13
2K0
非零环绕规则
简单说一下就是这个样子:对于路径中的任意给定区域,从该区域内部画一条足够长的线段,使此线段的终点完全露在路径范围之外。然后将计数器初始化为0,每当这条线段与路径上的直线或曲线相交时,就改变计数器的值。如果与路径顺时针部分相交的时候,则加1;如果与路径的逆时针部分相交的时候,则减1。如果最终值不是0,那么说明区域在路径的里面。
kai666666
2020/10/19
1.5K0
非零环绕规则
Canvas绘制八卦图
运用Canvas绘图编写一个八卦图效果。 最终效果如下: 代码实现如下: <!doctype html> <html lang="en"> <head> <meta charset="UTF
越陌度阡
2020/11/26
4780
Canvas绘制八卦图
【JS】928- 用 Canvas 编辑你的图片
大家好,我是 canvas ,我能让大家通过 canvas 标签,用JavaScript来绘制图形。除此之外,动画,游戏图形,数据可视化,照片处理和实时视频处理都难不倒我噢~
pingan8787
2021/04/26
4.6K0
【JS】928- 用 Canvas 编辑你的图片
Canvas 从入门到劝朋友放弃(图解版)
在前端领域,如果只是懂 Vue 或者 React ,未来在职场的竞争力可能会比较弱。
德育处主任
2022/09/02
2K0
Canvas 从入门到劝朋友放弃(图解版)
Canvas系列(2):曲线图形
我们的代码是加在上一章最后的坐标系中的,如果直接使用arc画弧的话,那么起始点是上一个绘制的结束,也就是绘制坐标系的结束位置,为了让之前的代码的结束不在作为本次绘制的开始,我们使用了新的APIcontext.beginPath();,用来开启一个新的路径,路径相关的知识会在下一章跟大家分享。我们这里绘制了一个圆心是(150,75),半径是60,从0度到90度的弧。由上我们可以看出弧的角度是按照我们高中学的坐标系来的。所以,学习是有用的!!!
kai666666
2020/10/19
1.1K0
Canvas系列(2):曲线图形
高仿一个echarts饼图
饼图,很常见的一种图表,使用任何一个图表库都能轻松的渲染出来,但是,我司的交互想法千奇百怪,布局捉摸不透,本身饼图是没啥可变的,但是配套的图例千变万化,翻遍ECharts配置文档都还原不出来,那么有两条路可以选,一是跟交互说实现不了,说服交互按图表库的布局来,但是一般交互可能会对你灵魂拷问,为什么别人都能做出来,你做不出来?所以我选第二种,自己做一个得了。
街角小林
2022/06/15
1.1K0
高仿一个echarts饼图
HTML5+CSS3+JavaScript从入门到精通-05
HTML5+CSS3+JavaScript从入门到精通 作者:王征,李晓波 第五章 HTML网页中的canvas绘图 案例 05-01 canvas元素 <!DOCTYPE html> <!--web05-01--> <!--canvas--> <html> <head> <meta charset="utf-8" /> <title>canvas元素</title> </head> <body> <h3 align="center">canvas元素</h3> <hr /
qiqi_fu
2021/12/03
1.2K0
HTML5+CSS3+JavaScript从入门到精通-05
canvas 实现自定义钟表
参考博客:https://www.cnblogs.com/liugang-vip/p/3557983.html
acoolgiser
2019/01/17
7010
canvas绘制动态圆环形进度条及参数详解
项目需要写一个圆形进度条,就尝试使用 canvas 写了一个,具体如下:上图是项目图片仅供参考,本文只介绍圆环及动效的实现。
德顺
2019/11/12
2K0
Canvas画图基础
画矩形 Canvas画矩形还是比较方便的,可以用fillrect,clearrect,strokerect,rect几种方法,各自间有点区别,先上代码: // html <canvas id="canvas" width="500" height="500" ></canvas> var canvas1 = document.getElementById("canvas"); var ctx = canvas1.getContext('2d'); ctx.strokeStyle = '#ff4444';
Bob.Chen
2018/05/02
2K0
Canvas画图基础
canvas练习 - 圆
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>canvas画圆</title> <style> canvas{ border:
xing.org1^
2018/10/10
6190
canvas练习 - 圆
Html5 学习系列(五)Canvas绘图API快速入门(2)
本文介绍了Canvas的基本用法,包括绘制文本、矩形、圆形、图像、动画、混合模式、缓存、绘制像素、阴影、裁剪、抗锯齿、半透明、Canvas3D以及一个自定义绘图的示例。通过这些基础用法,可以快速上手HTML5 Canvas,实现各种复杂的效果。
老马
2018/01/05
1.1K0
H5的canvas绘图技术
canvas元素是HTML5中新添加的一个元素,该元素是HTML5中的一个亮点。Canvas元素就像一块画布,通过该元素自带的API结合JavaScript代码可以绘制各种图形和图像以及动画效果。
小周sir
2019/09/23
1.1K0
H5的canvas绘图技术
Canvas入门到高级详解(上)
第三步:保存到插件的文件夹中,后缀名为:.sublime-snippet 比如我存放的位置: C:\Users\malunmac\AppData\Roaming\Sublime Text 3\Packages\User\snippets snippets 是我自己新建的文件夹。
老马
2019/05/25
1.8K0
简单的Canvas
ps:上面画内圆时用的moveTo()方法,其实就是“提笔”,首先用“笔”画了个外圆,然后将笔提起来,放到内圆的一点上,然后再画。
Ewall
2018/09/04
7070
简单的Canvas
可视化初探上
作为前端工程师,很多人的主要工作就是和网页打交道。那扪心自问一下,写了这么多网页之后,你是不是也想要做些尝试或者突破呢?如果是的话,我建议大家试试可视化。
年少轻狂12138
2022/08/10
1.8K1
可视化初探上
简单的canvas绘图
注意:默认情况下 <canvas> 元素没有边框和内容,width 和 height 属性定义的画布的大小.
江米小枣
2020/06/15
2.4K0
相关推荐
canvas扇形图、饼状图绘制
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档