千家信息网

Python中缓存lru_cache的方法是什么

发表于:2025-01-17 作者:千家信息网编辑
千家信息网最后更新 2025年01月17日,这篇文章主要讲解了"Python中缓存lru_cache的方法是什么",文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习"Python中缓存lru_cache
千家信息网最后更新 2025年01月17日Python中缓存lru_cache的方法是什么

这篇文章主要讲解了"Python中缓存lru_cache的方法是什么",文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习"Python中缓存lru_cache的方法是什么"吧!

一、前言

我们经常谈论的缓存一词,更多的类似于将硬盘中的数据存放到内存中以至于提高读取速度,比如常说的redis,就经常用来做数据的缓存。
Python的缓存(lru_cache)是一种装饰在被执行的函数上,将其执行的结果缓存起来,当下次请求的时候,如果请求该函数的传参未变则直接返回缓存起来的结果而不再执行函数的一种缓存装饰器。

二、举例说明

1.现在我们先不使用缓存来写一个求两数之和的函数,并调用执行它两次:

def test(a, b):    print('开始计算a+b的值...')    return a + bprint('1+2等于:', test(1, 2))print('1+2等于:', test(1, 2))

执行结果

开始计算a+b的值...
1+2等于: 3
开始计算a+b的值...
1+2等于: 3

可以看到test被执行了两次,现在我们加上缓存再进行执行:

from functools import lru_cache@lru_cachedef test(a, b):    print('开始计算a+b的值...')    return a + bprint(test(1, 2))print(test(1, 2))

执行结果

开始计算a+b的值...
1+2等于: 3
1+2等于: 3

可以看到test函数只被执行了一次,第二次的调用直接输出了结果,使用了缓存起来的值。

2.当我们使用递归求斐波拉契数列 (斐波那契数列指的是这样一个数列:0,1,1,2,3,5,8,它从第3项开始,每一项都等于前两项之和) 的时候,缓存对性能的提升就尤其明显了:

不使用缓存求第40项的斐波拉契数列

import datetimedef fibonacci(num):        # 不使用缓存时,会重复执行函数    return num if num < 2 else fibonacci(num - 1) + fibonacci(num - 2)start = datetime.datetime.now()print(fibonacci(40))end = datetime.datetime.now()print('执行时间', end - start)

执行时间

执行时间 0:00:29.004424

使用缓存求第40项的斐波拉契数列:

import datetimedef fibonacci(num):        # 不使用缓存时,会重复执行函数    return num if num < 2 else fibonacci(num - 1) + fibonacci(num - 2)start = datetime.datetime.now()print(fibonacci(40))end = datetime.datetime.now()print('执行时间', end - start)

执行时间

执行时间 0:00:00

两个差距是非常明显的,因为不使用缓存时,相当于要重复执行了很多的函数,而使用了lru_cache则把之前执行的函数结果已经缓存了起来,就不需要再次执行了。

三、lru_cache 用法

1.参数详解

查看lru_cache源码会发现它可以传递两个参数:maxsize、typed:

def lru_cache(maxsize=128, typed=False):    """Least-recently-used cache decorator.    If *maxsize* is set to None, the LRU features are disabled and the cache    can grow without bound.        ...        """

1) maxsize

代表被lru_cache装饰的方法最大可缓存的结果数量 (被装饰方法传参不同一样,则结果不一样;如果传参一样则为同一个结果), 如果不指定传参则默认值为128,表示最多缓存128个返回结果,当达到了128个时,有新的结果要保存时,则会删除最旧的那个结果。如果maxsize传入为None则表示可以缓存无限个结果;

2)typed

默认为false,代表不区分数据类型,如果设置为True,则会区分传参类型进行缓存,官方是这样描述的:

如果typed为True,则将分别缓存不同类型的参数,
例如,f(3.0)和f(3)将被视为具有明显的结果。

但在python3.9.8版本下进行测试,typed为false时,按照官方的测试方法测试得到的还是会被当成不同的结果处理,这个时候typed为false还是为true都会区别缓存,这与官方文档的描述存在差异:

from functools import lru_cache@lru_cachedef test(a):    print('函数被调用了...')    return aprint(test(1.0))print(test(1))

执行结果

函数被调用了...
1.0
函数被调用了...

但如果是多参数的情况下,则会被当成一个结果:

from functools import lru_cache@lru_cachedef test(a, b):    print('函数被调用了...')    return a , bprint(test(1.0, 2.0))print(test(1, 2))

执行结果

函数被调用了...
(1.0, 2.0)
(1.0, 2.0)

这个时候设置typed为true时,则会区别缓存:

from functools import lru_cache@lru_cache(typed=True)def test(a, b):    print('函数被调用了...')    return a , bprint(test(1.0, 2.0))print(test(1, 2))

执行结果

函数被调用了...
(1.0, 2.0)
函数被调用了...
(1, 2)

当传参个数大于1时,才符合官方的说法,不清楚是不是官方举例有误

2. lru_cache不支持可变参数

当传递的参数是dict、list等的可变参数时,lru_cache是不支持的,会报错:

from functools import lru_cache@lru_cachedef test(a):    print('函数被执行了...')    return aprint(test({'a':1}))

报错结果

TypeError: unhashable type: 'dict'

四、lru_cache 与redis的区别

缓存缓存位置是否支持可变参数是否支持分布式是否支持过期时间设置支持的数据结构需单独安装
redis缓存在redis管理的内存中支持5种数据结构
lru_cache缓存在应用进程的内存中,应用被关闭则被清空字典(参数为:key,结果为:value)

感谢各位的阅读,以上就是"Python中缓存lru_cache的方法是什么"的内容了,经过本文的学习后,相信大家对Python中缓存lru_cache的方法是什么这一问题有了更深刻的体会,具体使用情况还需要大家实践验证。这里是,小编将为大家推送更多相关知识点的文章,欢迎关注!

缓存 结果 函数 参数 方法 时间 支持 官方 数列 数据 时候 不同 内存 类型 波拉 可变 学习 测试 明显 两个 数据库的安全要保护哪些东西 数据库安全各自的含义是什么 生产安全数据库录入 数据库的安全性及管理 数据库安全策略包含哪些 海淀数据库安全审计系统 建立农村房屋安全信息数据库 易用的数据库客户端支持安全管理 连接数据库失败ssl安全错误 数据库的锁怎样保障安全 网络安全预防诈骗艺术字 rac数据库对外提供几个ip 图书数据库是否入无形资产 戴夫的服务器地址 有什么好的外贸软件开发 家庭用户能不能自建存储服务器 合肥hpe塔式服务器哪家好 软件开发什么项目挣钱 科技公司网络安全预算明细 加强学校网络安全意识的宣传 网络安全的技术种类及作用 城市数据库设计 生物学门类数据库英文 淘宝网络安全专家叫什么 窗口是数据库应用系统的工作窗口 成都服装进销存软件开发 财务软件开发工具官方正式版 增强网络安全意识日文 做好网络安全攻防演练的要求 关于数据库基本概念的题型 同江行业专业软件开发 互联网领先科技排名 杭州九匡网络技术有限公司招聘 新塘牛牛软件开发公司 民国申报数据库 连云港信息网络技术服务费 tp5数据库查询where portal认证服务器搭建 广电网络安全知识大全 服务器的小电风扇三线怎样接线
0