Python 迭代器与生成器
Python 中的迭代器和生成器是处理集合元素的重要工具,它们在处理大量数据时特别有用,因为它们不需要一次性将所有数据加载到内存中。
迭代器(Iterator)
迭代器是一个实现了迭代器协议的对象,这意味着它有两个方法:__iter__() 和 __next__()。
__iter__():返回迭代器对象本身。__next__():返回容器的下一个元素。
迭代器可以用来遍历任何集合对象,比如列表、元组、字典等。
创建迭代器
class MyIterator:def __init__(self, data):self.data = dataself.index = 0def __iter__(self):return selfdef __next__(self):if self.index < len(self.data):result = self.data[self.index]self.index += 1return resultelse:raise StopIteration# 使用迭代器
data = [1, 2, 3, 4, 5]
my_iter = MyIterator(data)
for item in my_iter:print(item)
迭代器的应用
迭代器通常用于以下情况:
- 遍历容器对象。
- 创建自定义容器对象。
- 在
for循环中使用。
迭代器和可迭代对象
在Python中,可迭代对象是指可以被iter()函数返回一个迭代器的对象。所有序列类型(如列表、元组、字符串)以及文件对象都是可迭代的。迭代器本身也是可迭代的,因为它们实现了__iter__()方法。
注意事项
- 迭代器只能向前移动,不能向后移动。
- 迭代器在遍历过程中,如果容器对象发生变化(例如添加或删除元素),迭代器的行为是未定义的。
- 迭代器在遍历结束后,需要重新创建一个新的迭代器来重新开始遍历。
生成器(Generator)
Python 生成器是一种特殊的迭代器,它允许你惰性地生成值,即一次只生成一个值,而不是一次性生成所有值。这种特性使得生成器在处理大数据集或无限序列时非常有用,因为它们可以帮助节省内存。
创建生成器
要创建一个生成器,你需要定义一个函数,并在函数体中使用yield关键字来产生值。每次调用生成器的__next__()方法时,函数会执行到下一个yield语句,并返回其值。当函数执行完毕或遇到return语句时,生成器会抛出StopIteration异常,表示迭代结束。
def simple_generator():yield 'hello'yield 'world'gen = simple_generator()
for value in gen:print(value)# 输出:
# hello
# world
生成器表达式
Python 还提供了生成器表达式,这是一种更简洁的方式来创建生成器。生成器表达式类似于列表推导式,但是使用圆括号而不是方括号。
gen_expr = (x * 2 for x in range(5))
for value in gen_expr:print(value)# 输出:
# 0
# 2
# 4
# 6
# 8
生成器高级用法
生成器不仅可以产生值,还可以接收外部传入的值,类似于函数的参数。
带参数的生成器
def generator_with_params(max_value):for i in range(max_value):yield igen = generator_with_params(5)
for value in gen:print(value)# 输出:
# 0
# 1
# 2
# 3
# 4
注意事项
- 生成器只能迭代一次。一旦迭代完成,生成器就会耗尽,除非重新创建。
- 你可以使用
next()函数来获取生成器的下一个值。- 你可以通过将生成器转换为列表来多次迭代,但这会消耗更多内存。
迭代器与生成器的区别
| 特性 | 迭代器 | 生成器 |
|---|---|---|
| 定义 | 实现了__iter__()和__next__()方法的对象。 | 使用yield关键字的函数自动成为生成器。 |
| 内存使用 | 通常需要存储所有元素,因此可能占用较多内存。 | 惰性计算,只在需要时产生下一个值,内存使用更高效。 |
| 实现方式 | 需要手动实现迭代器协议。 | 通过定义一个包含yield的函数自动实现。 |
| 使用方式 | 通过for循环或next()函数使用。 | 通过for循环或next()函数使用。 |
| 状态管理 | 需要手动管理迭代状态(如索引)。 | 由Python自动管理状态。 |
| 单次/多次使用 | 可以设计为可重置状态,实现多次迭代。 | 默认情况下只能迭代一次,迭代完成后不能再用。 |
| 功能丰富性 | 可以封装复杂的迭代逻辑。 | 可以包含条件语句、循环等,功能灵活。 |
| 转换为列表 | 直接使用list()函数。 | 需要使用list()函数转换,但可能消耗较多内存。 |
| 适用场景 | 适合已知元素数量且需要多次迭代的场景。 | 适合元素数量未知或数据量较大的场景,以及只需要单次迭代的场景。 |
迭代器的特点:
- 可重用性:迭代器可以被多次重用,只要重置其内部状态即可。
- 显式实现:需要显式实现
__iter__()和__next__()方法。 - 状态控制:迭代器提供了对迭代过程的完全控制,可以在迭代过程中修改其状态。
生成器的特点:
- 惰性计算:生成器只在需要时计算下一个值,这使得它们在处理大型数据集时更加内存高效。
- 简洁性:生成器通常比迭代器更简洁,因为它们不需要显式定义
__iter__和__next__方法。 - 单次使用:生成器只能被迭代一次,一旦迭代完成,就不能再次使用。
- 自动管理:Python自动管理生成器的状态,不需要手动管理。
迭代器和生成器都是Python中处理集合和序列的强大工具,选择使用哪一个取决于具体的应用场景和需求。
相关文章:
Python 迭代器与生成器
Python 中的迭代器和生成器是处理集合元素的重要工具,它们在处理大量数据时特别有用,因为它们不需要一次性将所有数据加载到内存中。 迭代器(Iterator) 迭代器是一个实现了迭代器协议的对象,这意味着它有两个方法&am…...
MySQL数据库——索引结构之B+树
本文先介绍数据结构中树的演化过程,之后介绍为什么MySQL数据库选择了B树作为索引结构。 文章目录 树的演化为什么其他树结构不行?为什么不使用二叉查找树(BST)?为什么不使用平衡二叉树(AVL树)&a…...
3_TCP/IP连接三次握手与断开四次挥手
TCP/IP 通信是网络通信的基础协议,分为以下主要步骤: 1、建立连接(三次握手) 目的:保证双方建立可靠的通信连接。 过程: 1>客户端发送 SYN:客户端向服务器发送一个 SYN(同步&…...
【LC】3159. 查询数组中元素的出现位置
题目描述: 给你一个整数数组 nums ,一个整数数组 queries 和一个整数 x 。 对于每个查询 queries[i] ,你需要找到 nums 中第 queries[i] 个 x 的位置,并返回它的下标。如果数组中 x 的出现次数少于 queries[i] ,该查…...
《机器学习》——KNN算法
文章目录 KNN算法简介KNN算法——sklearnsklearn是什么?sklearn 安装sklearn 用法 KNN算法 ——距离公式KNN算法——实例分类问题完整代码——分类问题 回归问题完整代码 ——回归问题 KNN算法简介 一、KNN介绍 全称是k-nearest neighbors,通过寻找k个距…...
GAMES101:现代计算机图形学入门-作业五
作业五 这次作业给了许多脚本,我们现在可以把每个脚本的代码逐行细细分析一下。 main.cpp #include "Scene.hpp" #include "Sphere.hpp" #include "Triangle.hpp" #include "Light.hpp" #include "Renderer.hpp&quo…...
GPU 进阶笔记(二):华为昇腾 910B GPU
大家读完觉得有意义记得关注和点赞!!! 1 术语 1.1 与 NVIDIA 术语对应关系1.2 缩写2 产品与机器 2.1 GPU 产品2.2 训练机器 底座 CPU功耗操作系统2.3 性能3 实探:鲲鹏底座 8*910B GPU 主机 3.1 CPU3.2 网卡和网络3.3 GPU 信息 3.3…...
Spring AOP:this 调用当前类方法无法被拦截
问题复现 假设我们正在开发一个宿舍管理系统,这个模块包含一个负责电费充值的类 ElectricService,它含有一个充电方法 charge(): Service public class ElectricService {public void charge() throws Exception {System.out.println("E…...
K8S-LLM:用自然语言轻松操作 Kubernetes
在 Kubernetes (K8s) 的日常管理中,复杂的命令行操作常常让开发者感到头疼。无论是部署应用、管理资源还是调试问题,都需要记住大量的命令和参数。Kubernetes 作为容器编排的行业标准,其强大的功能伴随着陡峭的学习曲线和复杂的命令行操作。这…...
lua和C API库一些记录
相关头文件解释 lua.h:声明lua提供的基础函数,所有内容都有个前缀lua_; luaxlib.h:声明辅助库提供的函数,所有内容都有个前缀luaL_; lualib.h:声明了打开标准库的函数; 辅助库对…...
SpringSecurity中的过滤器链与自定义过滤器
关于 Spring Security 框架中的过滤器的使用方法,系列文章: 《SpringSecurity中的过滤器链与自定义过滤器》 《SpringSecurity使用过滤器实现图形验证码》 1、Spring Security 中的过滤器链 Spring Security 中的过滤器链(Filter Chain)是一个核心的概念,它定义了一系列过…...
Slate文档编辑器-Decorator装饰器渲染调度
Slate文档编辑器-Decorator装饰器渲染调度 在之前我们聊到了基于文档编辑器的数据结构设计,聊了聊基于slate实现的文档编辑器类型系统,那么当前我们来研究一下slate编辑器中的装饰器实现。装饰器在slate中是非常重要的实现,可以为我们方便地…...
本地Docker部署Flowise并实现远程构建LLM应用程序原型高效开发
文章目录 前言1. Docker安装Flowise2. Ubuntu安装Cpolar3. 配置Flowise公网地址4. 远程访问Flowise5. 固定Cpolar公网地址6. 固定地址访问 前言 相信很多对AI感兴趣的小伙伴都会觉得正在逐渐流行的工作流自动化和AI集成特别酷炫,没错,这些技术像“秘密武…...
多点通信、流式域套接字
一、广播 1.1广播的发送端模型: #include<myhead.h>#define BEN_IP "192.168.191.129" #define BEN_PORT 8888#define PORT 6666int main(int argc, const char *argv[]) {int oldfd socket(AF_INET,SOCK_DGRAM,0);if(oldfd -1){perror("soc…...
vue3使用video-player实现视频播放(可拖动视频窗口、调整大小)
1.安装video-player npm install video.js videojs-player/vue --save在main.js中配置全局引入 // 导入视频播放组件 import VueVideoPlayer from videojs-player/vue import video.js/dist/video-js.cssconst app createApp(App) // 视频播放组件 app.use(VueVideoPlayer)2…...
模块化和面向接口的设计:深入理解和应用
模块化和面向接口的设计:深入理解和应用 在面向对象编程中,模块化 和 面向接口设计 是两种非常重要的编程理念。它们能帮助开发人员构建更加清晰、可维护和易于扩展的系统。接下来,我们将详细解释这两种设计思想,并结合 Python 中…...
《SwiftUI 实现点击按钮播放 MP3 音频》
功能介绍 点击按钮时,应用会播放名为 yinpin.mp3 的音频文件。使用 AVAudioPlayer 来加载和播放音频。 关键点: 按钮触发:点击按钮会调用 playAudio() 播放音频。音频加载:通过 Bundle.main.url(forResource:) 加载音频文件。播…...
微机接口课设——基于Proteus和8086的打地鼠设计(8255、8253、8259)Proteus中Unknown 1-byte opcode / Unknown 2-byte opcode错误
原理图设计 汇编代码 ; I/O 端口地址定义 IOY0 EQU 0600H IOY1 EQU 0640H IOY2 EQU 0680HMY8255_A EQU IOY000H*2 ; 8255 A 口端口地址 MY8255_B EQU IOY001H*2 ; 8255 B 口端口地址 MY8255_C EQU IOY002H*2 ; 8255 C 口端口地址 MY8255_MODE EQU IOY003H*2 ; …...
MySQL如何执行.sql 文件:详细教学指南
在使用MySQL数据库过程中,我们经常需要执行包含SQL语句的.sql文件。这些文件通常用于数据库的备份和恢复或批量执行SQL脚本。本文将详细介绍如何在不同环境下执行MySQL的.sql文件。 前置准备 在开始之前,请确保以下条件已经满足: 已经安装…...
非周期性脑活动的动态重构支持癫痫患者的认知功能:一种神经指纹识别方法
摘要 颞叶癫痫(TLE)的特征是大脑活动模式发生大规模的变化,并且这种变化与患者的认知功能受损密切相关。本研究旨在使用神经指纹方法分析大脑活动的动态重构,以描绘TLE患者的个体特征及其认知功能相关性。本研究收集了68名TLE患者和34名对照组的10min静息…...
springboot基于Hadoop的健康饮食推荐系统的设计与实现_5578bn9k_yh025
前言 随着人们生活水平的提高和健康意识的增强,越来越多的人开始关注自己的饮食习惯和健康状况。然而,传统饮食推荐方式往往缺乏个性化与数据支撑,难以满足用户多样化需求。SpringBoot基于Hadoop的健康饮食推荐系统应运而生,旨在为…...
记录复现多模态大模型论文OPERA的一周工作()投
pagehelper整合 引入依赖com.github.pagehelperpagehelper-spring-boot-starter2.1.0compile编写代码 GetMapping("/list/{pageNo}") public PageInfo findAll(PathVariable int pageNo) {// 设置当前页码和每页显示的条数PageHelper.startPage(pageNo, 10);// 查询数…...
Redis持久化:从AOF到RDB,如何实现数据不丢失?耐
Qt是一个跨平台C图形界面开发库,利用Qt可以快速开发跨平台窗体应用程序,在Qt中我们可以通过拖拽的方式将不同组件放到指定的位置,实现图形化开发极大的方便了开发效率,本笔记将重点介绍QSpinBox数值微调组件的常用方法及灵活应用。…...
告别‘选择困难症’:用Envelope Q-Learning让AI学会在《超级马里奥》里权衡金币与速度
告别‘选择困难症’:用Envelope Q-Learning让AI学会在《超级马里奥》里权衡金币与速度 想象一下,你正在玩《超级马里奥》,面对前方闪闪发光的金币和即将关闭的关卡大门,必须在"快速通关"和"收集财富"之间做出…...
VMware Workstation 16 中 Windows Server 2019 数据中心版安装与优化指南
1. VMware Workstation 16 环境准备 在开始安装 Windows Server 2019 数据中心版之前,我们需要先准备好 VMware Workstation 16 的环境。我建议大家在安装前检查下自己的电脑配置,毕竟跑虚拟机还是挺吃资源的。我的经验是,至少要有 16GB 内存…...
Matlab串口通信上位机开发:从零搭建实时数据采集系统(附完整代码)
Matlab串口通信上位机开发实战:从零构建工业级数据采集系统 在工业自动化、物联网设备调试和科研实验数据采集领域,串口通信作为最基础也最可靠的数据传输方式,至今仍发挥着不可替代的作用。Matlab凭借其强大的数值计算能力和丰富的可视化工具…...
Rust 时间处理神器:chrono 从入门到实战
Rust 时间处理神器:chrono 从入门到实战 在 Rust 生态中,chrono 凭借其遵循 ISO 8601 标准、支持时区、类型安全且性能优异的特性,成为了 Rust 开发者的首选工具。本文将从入门到进阶,并结合实际开发场景带你全面掌握 chrono 的使…...
柔性车间动态重调度实战:机器故障下的遗传算法优化策略
1. 柔性车间调度与机器故障的实战挑战 想象一下你正在管理一个汽车零部件生产车间,突然一台关键数控机床在下午3点15分突发故障,维修需要4小时。此时有10个不同型号的曲轴正在排队等待加工,每道工序都有多个备选设备但加工效率各不相同。这就…...
Qwen3.5-9B实战教程:WebSocket流式响应+前端实时渲染优化方案
Qwen3.5-9B实战教程:WebSocket流式响应前端实时渲染优化方案 1. 项目概述与核心能力 Qwen3.5-9B是一款拥有90亿参数的开源大语言模型,在多个领域展现出强大的能力: 强逻辑推理:能够处理复杂的逻辑问题,适合需要深度…...
在CentOS 7虚拟机里,搞定Cadence IC618版图DRC的License报错(附MAC地址修改法)
在CentOS 7虚拟机中彻底解决Cadence IC618版图DRC的License绑定问题 当你在VMware虚拟机的CentOS 7系统中使用拷贝安装的Cadence IC618进行版图设计时,DRC验证阶段可能会遇到令人头疼的"licensed sufficiently"报错。这个问题通常与虚拟环境的网络配置和L…...
