在 Nodejs 和 TypeScript 中使用 LRU 缓存

高效利用 node.js 和 typescript 构建 lru 缓存机制

在构建 Web 应用时,我们经常会遇到耗时操作,例如计算密集型任务或昂贵的外部 API 调用。 缓存技术能有效解决这个问题,通过存储操作结果,避免重复计算或调用。本文将演示如何使用 lru-cache 包在 Node.js 中结合 TypeScript 实现 LRU (Least Recently Used) 缓存。

LRU 缓存设置

首先,安装 lru-cache 包:

npm install lru-cache

接下来,创建一个最大容量为 5 的 LRU 缓存来存储用户数据:

import { LRUCache } from 'lru-cache';

interface User {
    id: number;
    name: string;
    email: string;
}

const userCache = new LRUCache<number, User>({ max: 5 });

模拟 API 数据获取

我们用一个模拟函数 fetchUserFromApi 模拟从外部 API 获取用户数据。该函数包含一个延迟,模拟网络请求耗时:

async function fetchUserFromApi(userId: number): Promise<User | null> {
    console.log(`Fetching user data for ID: ${userId} from API...`);
    await new Promise(resolve => setTimeout(resolve, 500));

    const users: User[] = [
        { id: 1, name: 'Alice', email: 'alice@example.com' },
        { id: 2, name: 'Bob', email: 'bob@example.com' },
        { id: 3, name: 'Charlie', email: 'charlie@example.com' },
    ];

    const user = users.find(user => user.id === userId);
    return user || null;
}

使用 LRU 缓存

getUser 函数利用 LRU 缓存:首先检查缓存中是否存在用户数据,若存在则直接返回;否则,从 API 获取数据并添加到缓存中。

async function getUser(userId: number): Promise<User | null> {
    const cachedUser = userCache.get(userId);

    if (cachedUser) {
        console.log(`User data for ID: ${userId} found in cache.`);
        return cachedUser;
    }

    const user = await fetchUserFromApi(userId);
    if (user) {
        userCache.set(userId, user);
    }
    return user;
}

测试 LRU 缓存

主函数 main 发出多个用户数据请求,演示缓存机制和 LRU 淘汰策略:

async function main() {
    // ... (identical to the original code, with minor formatting changes) ...
}

main();

LRU 缓存的工作原理及优势

首次请求用户数据时,数据来自 API。再次请求相同用户时,数据直接从缓存获取,提升速度。 LRU 缓存最大容量为 5,当请求超过容量时,最久未使用的数据会被淘汰。

使用 LRU 缓存能减少 API 负载,提升应用性能,节省资源。

总结

本文演示了如何在 Node.js 中使用 lru-cache 包结合 TypeScript 构建 LRU 缓存机制,有效提高应用效率。 如有任何疑问,欢迎留言。

以上就是在 Nodejs 和 TypeScript 中使用 LRU 缓存的详细内容,更多请关注骃骐网【www.myinqi.com】。

相关推荐:

如何解决Python安装程序卡在预编译编译环节_关闭杀毒软件或清理缓存文件

pip卡在“Building wheel”或“Resolving packages…”主因是本地依赖解析或C++源码编译,非网络问题;关对进程、手动清缓存目录(如%LOCALAPPDATA%\pip\Cache或~/.cache/pip/Cache)、禁用杀软实时防护可解决多数情况。 Python安装程序卡在“Building wheel”或“Resolving packages…”不是网络慢,而...

Python如何实现一致性哈希算法_解决分布式缓存数据分配不均

一致性哈希通过固定哈希空间(如2^32)构建环形结构,节点和数据映射其上并顺时针就近分配;增删节点仅影响邻近区间,大幅减少数据迁移;引入虚拟节点可缓解物理节点分布不均问题,提升负载均衡性。 直接用 hash_ring 库最省事,但真要自己写、调参或排查分布不均问题,必须理解虚拟节点数量、哈希函数输出范围、环结构更新时机这三个关键点。 为什么简单取模(hash(key) % N)在节点变动时会崩 节...

如何优化Python Django模板渲染性能_开启Cached Template Loader缓存

cached.Loader不生效通常是配置位置错误,它必须作为包装器嵌套配置,将其他loader置于其参数列表中,而非与之并列;其缓存位于进程内存,依赖文件修改时间,重启服务才能刷新,且与Django的CACHES设置无关。 cached.Loader 不生效,八成是配置写错了位置,不是缓存没起作用,而是根本没被用上。 cached.Loader 配置必须嵌套,不能并列 它不是和 filesyst...

为什么Python循环中调用len方法性能低_提前缓存变量长度减少调用

应缓存len()结果以避免重复开销:当容器长度不变且循环次数≥1000时,用data_len = len(data)提前缓存;enumerate和zip可替代range(len());海象运算符:=适合单次条件判断。 len()在循环条件中反复调用会拖慢速度 Python 的 len() 确实是 O(1) 操作,但每次调用仍要经过名称查找、函数分派、对象方法调用(obj.__len__())三步。...

什么是Python的.pyc文件_环境搭建中关于字节码缓存的深度解析

.pyc 文件是 Python 源码编译生成的字节码缓存文件,仅用于加速模块导入;它非必需,不跨版本兼容,仅在 import 时生成,存于 pycache 中并受 magic number 校验。 什么是 .pyc 文件?它不是编译产物,而是字节码缓存 .pyc 文件是 Python 源码(.py)被编译成字节码后,序列化写入磁盘的二进制文件。它不是像 C 的 .o 那样的“可执行目标文件”,也不...

如何在Python中实现异步的缓存系统_结合aioredis与LRU算法优化访问

因为@lru_cache是同步装饰器,无法处理async def返回的协程对象,直接使用会导致未await警告或静默错误。 为什么不能直接用 @lru_cache 装饰异步函数 因为 @lru_cache 是同步装饰器,它内部调用的是普通函数对象,而 async def 定义的函数返回的是协程对象(coroutine),不是可哈希的返回值。直接套用会导致缓存命中时返回一个未 await 的协程,后...

如何优化Python反射机制性能_利用getattr缓存加速属性获取

getattr频繁调用慢是因为每次都要执行完整属性查找链,涉及多次字典查找和函数调用;缓存可提速3.2倍,适用固定对象+固定属性、固定对象+动态方法名、固定类+固定类变量三类场景。 getattr频繁调用为什么慢? 每次调用 getattr(obj, "attr") 都会触发完整的属性查找链:先查实例 __dict__,再查类、父类、描述符、__getattr__ 方法……这个过程涉及多次字典查找...

Python如何生成并写入临时文件且自动销毁_使用tempfile模块管理缓存数据

NamedTemporaryFile写完打不开是因为默认delete=True,close()后文件立即被系统删除;需设delete=False并手动unlink,或改用mkstemp()获取稳定路径。 tempfile.NamedTemporaryFile 为什么写完就打不开? 因为默认 delete=True,且文件句柄关闭后系统立即删除——不是“等程序退出”,而是 close() 调用后瞬间...

如何在Python中实现LRU与LFU缓存策略对比_通过functools.lru_cache装饰器

functools.lru_cache仅实现LRU策略,不记录访问频次、无频次统计接口,且装饰器封装过深无法修改;其底层用双向链表+字典维护时序,不支持LFU所需频次维度,强行改造会破坏缓存一致性。 为什么 functools.lru_cache 不能直接做 LFU 对比 lru_cache 是纯 LRU(最近最少使用)策略,底层用双向链表 + 字典维护访问时序,每次 get 都把键移到链表头。它...

C++循环优化有哪些技巧 循环展开与缓存友好访问

循环展开和缓存友好访问可显著提升C++程序性能。循环展开通过减少迭代次数并增加每次操作量来降低控制开销,提高指令并行性,但需处理余数和代码膨胀问题;现代编译器可在-O3等优化级别下自动展开。缓存友好访问则强调顺序、连续内存访问,优先行主序遍历多维数组,结合分块(tiling)技术提升缓存命中率,并通过内存对齐减少缓存行分裂。两者结合使用,辅以编译器优化(如PGO、simd、restrict),能有...