python 可迭代,迭代器,生成器,装饰器

news/2024/10/15 19:33:29/

1. 可迭代(Iterable)

可迭代 是指一个对象可以返回一个迭代器的对象。也就是说,它实现了 __iter__() 方法或 __getitem__() 方法。常见的可迭代对象有列表、元组、字符串、字典和集合。

from collections.abc import Iterablei = 100
s = "hello"
l = [1, 2, 3]
t = (1, 2, 3)
d = {"name": "qiku"}
set0 = {1, 2, 3}print(isinstance(i, Iterable),  # False, 整数不可迭代isinstance(s, Iterable),  # True, 字符串可迭代isinstance(l, Iterable),  # True, 列表可迭代isinstance(t, Iterable),  # True, 元组可迭代isinstance(d, Iterable),  # True, 字典可迭代(迭代的是键)isinstance(set0, Iterable) # True, 集合可迭代
)

2. 迭代器(Iterator)

迭代器 是一个对象,它实现了 __iter__()__next__() 方法(在 Python 3 中,__next__() 方法被称为 __next__())。迭代器可以用于遍历序列中的元素,每次调用 __next__() 方法时,它返回序列中的下一个元素。迭代器在遍历完所有元素后会抛出 StopIteration 异常。

from collections.abc import Iterable, Iterator  # 从 collections.abc 模块导入 Iterable 和 Iteratorclass MyDatas:def __init__(self, n):# 初始化数据列表,从 1 到 nself.datas = [i for i in range(1, n + 1)]self.current_index = 0  # 当前索引,初始化为 0def __iter__(self):# 返回自身,因为它既是可迭代对象也是迭代器return selfdef __next__(self):# 如果当前索引超出数据列表的长度,抛出 StopIteration 异常,表示迭代结束if self.current_index >= len(self.datas):raise StopIterationelse:# 返回当前索引的数据,并将当前索引加 1current = self.datas[self.current_index]self.current_index += 1return currentmd = MyDatas(5)  # 创建一个包含 1 到 5 的 MyDatas 实例# 打印 md 是否是 Iterable 和 Iterator
print(isinstance(md, Iterable), isinstance(md, Iterator))# 遍历 MyDatas 实例中的所有数据
for d in md:print(d)

3. 生成器(Generator)

生成器 是一种特殊类型的迭代器,使用函数和 yield 关键字来创建。生成器函数可以像普通函数一样定义,但它们使用 yield 来返回值,而不是 return。每次调用生成器的 __next__() 方法时,它会从上次 yield 语句处继续执行,直到遇到下一个 yield 语句或函数结束。

# 定义一个列表 l0,并打印其内存大小
l0 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19]
print(l0.__sizeof__())  # 打印 l0 列表在内存中占用的字节数
print(l0[15])  # 打印列表中索引为 15 的元素# 定义一个生成器表达式 t0,并打印其内存大小
t0 = (i for i in range(1, 1000000000))
print(t0.__sizeof__())  # 打印生成器 t0 在内存中占用的字节数
print(isinstance(t0, Iterable), isinstance(t0, Iterator), isinstance(t0, Generator))  
# 打印 t0 是否是 Iterable、Iterator 和 Generator 类型
print(next(t0), next(t0))  # 打印生成器 t0 的前两个值# 定义一个生成器函数 my_datas
def my_datas():yield 1yield 2yield 3yield 10yield 20yield 30return 100  # 生成器结束时返回的值r = my_datas()  # 创建生成器对象 rprint(type(r))  # 打印生成器对象 r 的类型# 使用 while 循环遍历生成器 r 的所有值
while True:try:print(next(r))  # 打印生成器 r 的下一个值except StopIteration as e:  # 捕捉 StopIteration 异常,表示生成器已结束print("取完了", e)  # 打印生成器结束时返回的值break  # 退出循环

生成器在内存中占用的字节数通常是固定的,比如在上述例子中是 184 字节。即使列表的元素数量增加,生成器的内存占用也不会显著增加。相比之下,当列表中的元素数量增加时,其内存占用量会显著增长。这是因为列表需要为每个元素分配额外的内存来存储数据。而生成器只在需要时生成数据,因而在处理大量数据时,生成器通常比列表更加节省内存。

4. 装饰器(Decorator)不改变函数原有实现给函数添加新功能

装饰器 是一种用于修改或扩展函数或方法行为的设计模式。装饰器是一个函数,它接受一个函数作为参数,并返回一个新的函数。它们常用于日志记录、权限检查、缓存等。

import time
import random# 定义一个装饰器函数 cost_time,用于计算函数执行时间
def cost_time(f):# 定义内部函数 calc,计算并打印被装饰函数的执行时间def calc():start = time.time()  # 记录开始时间f()  # 调用被装饰的函数print(f"函数{f.__name__}开销:{time.time() - start}")  # 计算并打印执行时间return calc  # 返回内部函数 calc# 生成一个包含 10000 个随机整数的列表 datas
datas = [random.randint(0, 10000) for i in range(10000)]
# 创建 datas 的副本 datas2
datas2 = datas.copy()# 使用 cost_time 装饰器装饰 my_sort1 函数
@cost_time
def my_sort1():datas.sort(reverse=True)  # 对列表 datas 进行降序排序print(datas)  # 打印排序后的列表# 使用 cost_time 装饰器装饰 my_sort2 函数
@cost_time
def my_sort2():datas3 = sorted(datas2, reverse=True)  # 对列表 datas2 进行降序排序,并生成新列表 datas3print(datas3)  # 打印排序后的新列表# 调用装饰后的 my_sort1 函数,计算其执行时间并打印排序结果
my_sort1()# 调用装饰后的 my_sort2 函数,计算其执行时间并打印排序结果
my_sort2()


http://www.ppmy.cn/news/1512563.html

相关文章

MySQL中处理JSON数据一文即可入门

MySQL从5.7版本开始原生支持JSON数据类型,使得在数据库中存储和查询JSON数据变得更加方便和高效。下面将介绍如何在MySQL中处理JSON数据,包括如何存储、查询和修改JSON数据。 1. 创建包含JSON列的表 首先,你需要创建一个表,该表…

招商期货:以超融合支撑期货重要业务,承载80%信创系统

招商期货有限公司(以下简称“招商期货”)成立于 1993 年,是招商证券股份有限公司的全资子公司,注册资本 35.98 亿元,是中国首批券商全资控股期货公司。 随着数字化进程快速推进、交易模式不断创新,系统建设…

Postman断言

目录 概述 断言工作原理 常用断言方法 Status code: Code is 200 Status code: Successful POST request Status code: Code name has string Response body: Contains string Response body: JSON value check Response body: ls equal to a string Response headers…

实现多goroutine之间的发布和订阅

实现多goroutine之间的发布和订阅 一、实现思路 一个发布者,三个订阅者发布者需要跟每个订阅者之间,都要建立一个chan调用发布方法后,三个订阅者都能收到发布的信息在发布和接收之间,增加暂停,使运行结果更加直观 二…

在亚马逊云科技上对Stable Diffusion模型提示词、输出图像内容进行安全审核

项目简介: 小李哥将继续每天介绍一个基于亚马逊云科技AWS云计算平台的全球前沿AI技术解决方案,帮助大家快速了解国际上最热门的云计算平台亚马逊云科技AWS AI最佳实践,并应用到自己的日常工作里。 本次介绍的是如何在亚马逊云科技机器学习托…

仿Muduo库实现高并发服务器——LoopThreadPool模块

这个模块需要具备那些基础知识。 线程创建相关操作,锁,条件变量。 设置线程数量: _thread_count 是线程池中,记录线程数量的成员。 创建线程池: 上图就是线程池的创建,将线程与EventLoop对象 通过数组下…

docker部署MySQL5.7.43并使用python脚本插入数据——实施案例

目录 一、配置docker环境 1. 阿里云镜像站配置docker环境 1. 安装必要的一些系统工具 ​编辑 2. 添加软件源信息 ​编辑 3. 修改 Docker 的 YUM 仓库配置文件,将 Docker 官方仓库的地址替换为阿里云的镜像源,以提高下载速度。 4. 更新并安装Dock…

ChatGLM-4-9b-chat本地化|天翼云GPU上vLLM本地部署开源模型完整攻略

“ 拥有一个私有化的领先国产开源大模型?本文详细介绍了如何在天翼云GPU上使用vLLM部署ChatGLM-4-9b-chat本地化模型的完整攻略,助您快速上手。” 01 — vLLM 本来打算用ollama在GPU服务器上部署开源模型GLM4,在之前文章有部署教程&#xff1…