快速提示:了解 Python 中的 Yield 关键字

感谢Shaumik Daityari帮助对本文进行同行评审。

当我们在 Python 中调用一个函数时,该函数通常会开始工作,直到遇到 a returnexception或到达其结尾——之后它将控制权返回给调用者。每当您再次调用该函数时,该过程将从头开始

假设你让一个人跟踪路上的红色汽车。该人将不断收到一个问题,询问他们是否发现了一辆红色汽车,而该人反过来会回答“是”或“否”。如果这个人回答“是”,红色汽车被发现的次数将会增加。

让我们看看如何在 Python 中做到这一点:

import time

def red_cars(answer):
    n = 0
    while True:
        if answer == 'yes':
            n = n + 1
            return n
        else:
            return n

stop = time.time() + 5 * 60
while time.time() < stop:
    answer = raw_input('Did you spot a red car on the road? ("yes" or "no"): ')
    times = red_cars(answer)
    print 'You have spotted ' + str(times) + ' cars so far!'

如果你运行这个程序,你会注意到什么?您是否注意到回答“是”的次数总是上限为1,而当您回答“否”时,0无论之前回答“是”,次数都会增加?

这就是 Python 的yield关键字发挥作用的地方。yield是我们暂时将控制权交给调用者的一种方式,并期望从控制权移交的那一点继续。

在给出上述示例的解决方案之前,让我演示一个非常简单的示例,以更好地说明其yield工作原理。

假设我们有以下简单的 Python 脚本:

def step_by_step():
    return 'step 1'
    return 'step 2'
    return 'step 3'
    
step = step_by_step()
for i in range (3):
    print step

如果运行脚本,您将获得以下输出:

step 1
step 1
step 1

现在,如果我们yield改为使用,如下所示:

def step_by_step():
    yield 'step 1'
    yield 'step 2'
    yield 'step 3'
    
step = step_by_step()
for i in range (3):
    print step.next()

输出如下:


step 1
step 2
step 3

如您所见,我们能够创建一系列值,因为对于每次调用,函数都会从产生值的点继续。这种类型的函数称为生成器。这样的函数创建了一个生成器迭代器,就像每次调用next()我们移动到下一条yield语句的方法一样。

如果我们回到我们的主要示例(红色汽车),可以编写如下来执行所需的任务:

import time

def red_cars(answer = None):
    n = 0
    while True:
        if answer=="yes":
            n = n + 1
            answer = yield n
        else:
            answer = yield n

car_color = red_cars()
car_color.next()

stop = time.time() + 5 * 60
while time.time() < stop:
    answer = raw_input('Did you spot a red car on the road? ("yes" or "no"): ')
    print 'You have spotted ' + str(car_color.send(answer)) + ' cars so far!'

因此,正如我们所看到的,yield当我们有兴趣在函数(生成器)退出的最后一点恢复执行时,以及我们也有兴趣在不同调用之间保持局部变量的值时,这被认为很重要——这与普通函数不同,其中这些值在退出函数时被销毁。

但是,还有其他用途yield。例如,yield如果您有一个返回序列的函数(例如,Excel 工作表中的行)并且您需要迭代序列而不同时将每个值都保存在内存中,则可以使用该函数。也就是节省内存。

yield也可以在使用 iterables 时使用,我们有一个很难在函数之间传递的大列表。例如,Python 在itertools 模块中用于排列和组合的内置函数使用yield.如果对Python有兴趣,想了解更多的Python以及AIoT知识,解决测试问题,以及入门指导,帮你解决学习Python中遇到的困惑,我们这里有技术高手。如果你正在找工作或者刚刚学校出来,又或者已经工作但是经常觉得难点很多,觉得自己Python方面学的不够精想要继续学习的,想转行怕学不会的, 都可以加入我们,可领取最新Python大厂面试资料和Python爬虫、人工智能、学习资料!微信公众号【Python大本营】等你来玩奥~

<think>根据用户需求,用户想要获取Python所有关键字的说明。我将根据Python 3.11版本的关键字进行说明,因为不同版本可能会略有不同。在Python中,我们可以通过`keyword`模块来获取当前版本的关键字列表及其说明。 步骤: 1. 导入keyword模块。 2. 获取关键字列表:`keyword.kwlist`。 3. 对每个关键字进行简要说明。 注意:由于关键字数量较多,我将用表格形式列出,并在回答中提供每个关键字的简要说明。但考虑到回答的格式要求,我将使用文本列表,并确保每个关键字用行内数学表达式的格式(即用$...$)包裹,但注意关键字本身是英文单词,不需要数学公式,因此这里实际上不需要使用$...$,而是直接列出。不过根据指令,变量名等应该使用$...$,但关键字作为代码,我们可以用反引号包裹(因为指令要求行内数学表达式,但关键字不是数学表达式,所以这里我们按照代码的常规表示,用反引号)。然而指令要求所有行内数学表达式必须用$...$,所以我们将关键字视为代码变量,使用$...$包裹。 但是,请注意:指令要求“所有行内数学表达式(包括变量、不等式、方程等)必须使用$...$格式”,而关键字是代码中的保留字,我们可以将其视为变量的一种特殊形式,所以用$...$包裹关键字。 例如:$if$, $else$ 等。 然而,在说明中,我们可能会提到一些函数名或变量名,同样用$...$包裹。 但是,整个关键字的列表和说明会很长,我们需要保证清晰和易读。 我将按照以下格式: 关键字:说明 另外,用户提到参考了站内引用,其中引用[1]提到了一些注意事项,引用[2]是关于$in$关键字的例子。我会在适当的地方引用。 由于关键字有35个(Python3.11),我将全部列出并给出简短说明。 注意:在Python中,关键字是区分大小写的,全部为小写。 开始编写回答: </think> 以下是Python 3.11版本的全部35个关键字及其详细说明(按字母顺序排列),严格遵循Python官方文档规范: ### 关键字说明表 | 关键字 | 说明 | |-------------|----------------------------------------------------------------------| | **$False$** | 布尔类型的假值,表示逻辑假。 | | **$None$** | 表示空值或无值的特殊对象,常用于函数无返回值时。 | | **$True$** | 布尔类型的真值,表示逻辑真。 | | **$and$** | 逻辑与运算符,当左右表达式均为真时返回真。 | | **$as$** | 为导入模块或异常创建别名,例如:`import numpy as np`。 | | **$assert$**| 调试断言,条件为假时抛出`AssertionError`。 | | **$async$** | 声明异步函数(协程函数),需配合`await`使用。 | | **$await$** | 在异步函数中暂停执行,等待协程完成。 | | **$break$** | 跳出当前循环(`for`或`while`),执行后续代码。 | | **$class$** | 定义类,例如:`class Student: ...`。 | | **$continue$**| 跳过当前循环剩余语句,进入下一次迭代。 | | **$def$** | 定义函数,例如:`def calculate(): ...`。 | | **$del$** | 删除对象引用,例如:`del list[0]`。 | | **$elif$** | `if`语句的分支条件,等同于"else if"。 | | **$else$** | `if`/`for`/`while`/`try`语句的最终分支。 | | **$except$**| 捕获`try`代码块中的异常,需指定异常类型。 | | **$finally$**| 无论是否发生异常,`try`语句结束后必然执行的代码块。 | | **$for$** | 迭代循环,例如:`for i in range(5): ...`。 | | **$from$** | 从模块导入特定对象,例如:`from math import sqrt`。 | | **$global$**| 声明全局变量,例如:`global count`。 | | **$if$** | 条件判断语句,控制代码执行分支。 | | **$import$**| 导入模块,例如:`import os`。 | | **$in$** | 成员检测符,判断元素是否在容器中(如列表、元组等)[^2]。 | | **$is$** | 对象身份比较,判断两个变量是否引用同一内存对象。 | | **$lambda$**| 创建匿名函数,例如:`add = lambda x,y: x+y`。 | | **$nonlocal$**| 声明闭包函数中的非局部变量(非全局)。 | | **$not$** | 逻辑非运算符,反转布尔值。 | | **$or$** | 逻辑或运算符,任一表达式为真时返回真。 | | **$pass$** | 空操作占位符,保持语法完整性。 | | **$raise$** | 手动触发异常,例如:`raise ValueError("Invalid input")`。 | | **$return$**| 从函数返回值,无参数时返回`None`。 | | **$try$** | 异常处理代码块,需配合`except`/`finally`使用。 | | **$while$** | 条件循环语句,条件为真时重复执行代码块。 | | **$with$** | 上下文管理器,自动管理资源(如文件操作)。 | | **$yield$** | 生成器函数返回值,暂停函数状态下次继续执行。 | ### 关键注意事项 1. **禁止用作标识符**:以上关键字不可用于变量/函数/类名(如命名`class=5`会触发`SyntaxError`)[^1]。 2. **大小写敏感**:所有关键字均为小写(`True`有效,`TRUE`无效)。 3. **完整列表获取**:可通过代码动态查看: ```python import keyword print(keyword.kwlist) # 输出当前版本所有关键字 ``` 4. **保留字规避**:使用IDE编写代码时,关键字通常会被高亮提示,避免误用[^1]。 > 提示Python关键字列表随版本更新可能变化,建议通过`keyword.kwlist`获取当前环境确切列表。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值