1. 引言
前情提要:
《redis 从0到1完整学习 (一):安装&初识 redis》
《redis 从0到1完整学习 (二):redis 常用命令》
《redis 从0到1完整学习 (三):redis 数据结构》
《redis 从0到1完整学习 (四):字符串 SDS 数据结构》
《redis 从0到1完整学习 (五):集合 IntSet 数据结构》
《redis 从0到1完整学习 (六):Hash 表数据结构》
《redis 从0到1完整学习 (七):ZipList 数据结构》
《redis 从0到1完整学习 (八):QuickList 数据结构》
《redis 从0到1完整学习 (九):SkipList 数据结构》
《redis 从0到1完整学习 (十):RedisObject 数据结构》
《redis 从0到1完整学习 (十一):RedisObject 之 String 类型》
《redis 从0到1完整学习 (十二):RedisObject 之 List 类型》
《redis 从0到1完整学习 (十三):RedisObject 之 Set 类型》
《redis 从0到1完整学习 (十四):RedisObject 之 ZSet 类型》
《redis 从0到1完整学习 (十五):RedisObject 之 Hash 类型》
《redis 从0到1完整学习 (十六):内存回收之 key 过期处理策略》
之前我们介绍了 redis 的内存回收的 key 过期的处理策略,本文接着主要介绍 redis 内存淘汰策略以及内存淘汰策略的配置方法。
2. redis 源码下载
Redis 源码可以点击这里下载,方便查看其中定义的一些数据结构。
3. 内存回收策略
Redis 内存淘汰策略:当 Redis 服务器的内存使用达到预设的最大限制时,为了防止内存溢出,Redis 会按照配置的淘汰策略来决定如何删除部分数据以回收内存。以下是一些主要的内存淘汰策略:
-
noeviction:
- 默认策略。不进行任何内存淘汰,当内存不足以容纳新写入的数据时,所有会导致内存增加的操作(如
SET
、LPUSH
等)都会返回错误。
- 默认策略。不进行任何内存淘汰,当内存不足以容纳新写入的数据时,所有会导致内存增加的操作(如
-
volatile-lru:
- 仅对设置了过期时间(TTL)的键进行淘汰,采用 LRU(Least Recently Used,最近最少使用)算法,即优先移除最近最少访问且已过期的键。
-
allkeys-lru:
- 对所有键(包括未设置过期时间的键)应用 LRU 算法,选择整个数据库中最久未使用的键进行淘汰。
-
volatile-lfu:
- 同样只针对设置了过期时间的键,但采用 LFU(Least Frequently Used,最不经常使用)算法,根据键的历史访问频率来淘汰访问次数最少的键。
-
allkeys-lfu:
- 对于所有键(无论是否设置过期时间)都使用 LFU 算法,淘汰整体上访问频率最低的键。
-
volatile-random:
- 随机淘汰一个已设置过期时间的键。
-
allkeys-random:
- 随机淘汰任意一个键,不论其是否设置了过期时间。从 db->dict (db的数据结构参考上一节)中随机挑选
-
volatile-ttl:
- 根据键的剩余生存时间(TTL)来淘汰,优先淘汰即将过期的键,即 TT L越小,越先淘汰。
4. 如何设置内存淘汰策略
在实际应用中,应根据业务场景需求来选择合适的淘汰策略。Redis 4.0 及以后版本还引入了更精细化的内存管理功能,例如可配置的 LFU 和 LRU 淘汰阈值以及混合淘汰策略。同时,Redis提供了配置选项允许用户自定义内存最大使用量,并可以配合配置文件或运行时动态调整内存淘汰策略。
Redis 设置内存淘汰策略可以在配置文件中进行,或者在运行时动态调整。以下是两种方法的详细步骤:
4.1 在 Redis 配置文件设置(推荐重启后生效)
打开 Redis 的配置文件 redis.conf
,找到与内存淘汰策略相关的配置项 maxmemory-policy
或 maxmemory
,并根据需要进行修改。
例如,要设置为 LRU 淘汰策略(当所有键都参与淘汰时),可以添加或修改以下行:
maxmemory <your_memory_limit_in_bytes>
maxmemory-policy allkeys-lru
这里的 <your_memory_limit_in_bytes>
应替换为你的 Redis 实例希望使用的最大内存大小,单位是字节。
4.2 运行时动态调整
对于已经运行中的 Redis 实例,可以通过执行命令来动态调整内存淘汰策略:
config set maxmemory <your_memory_limit_in_bytes>
config set maxmemory-policy <policy_name>
其中 <your_memory_limit_in_bytes>
是新的内存限制值,而 <policy_name>
可以是以下之一:
- noeviction
- volatile-lru
- allkeys-lru
- volatile-lfu
- allkeys-lfu
- volatile-random
- allkeys-random
- volatile-ttl
- noeviction (自 Redis 6.0 开始还支持lfu、volatile-lfu)
例如,若要在运行时将淘汰策略改为 LRU 并设置内存限制为 1GB,则执行:
redis-cli config set maxmemory 1073741824
redis-cli config set maxmemory-policy allkeys-lru
请注意,动态调整内存限制和策略可能会导致立即开始淘汰数据,因此请谨慎操作并在理解业务场景后再做决定。同时,如果已达到内存上限,在不增加可用内存的情况下更改策略可能无法立即缓解内存压力。
5. 参考
《redis 从0到1完整学习 (一):安装&初识 redis》
《redis 从0到1完整学习 (二):redis 常用命令》
《redis 从0到1完整学习 (三):redis 数据结构》
《redis 从0到1完整学习 (四):字符串 SDS 数据结构》
《redis 从0到1完整学习 (五):集合 IntSet 数据结构》
《redis 从0到1完整学习 (六):Hash 表数据结构》
《redis 从0到1完整学习 (七):ZipList 数据结构》
《redis 从0到1完整学习 (八):QuickList 数据结构》
《redis 从0到1完整学习 (九):SkipList 数据结构》
《redis 从0到1完整学习 (十):RedisObject 数据结构》
《redis 从0到1完整学习 (十一):RedisObject 之 String 类型》
《redis 从0到1完整学习 (十二):RedisObject 之 List 类型》
《redis 从0到1完整学习 (十三):RedisObject 之 Set 类型》
《redis 从0到1完整学习 (十四):RedisObject 之 ZSet 类型》
《redis 从0到1完整学习 (十五):RedisObject 之 Hash 类型》
《redis 从0到1完整学习 (十六):内存回收之 key 过期处理策略》
欢迎关注本人,我是喜欢搞事的程序猿; 一起进步,一起学习;
也欢迎关注我的wx公众号:一个比特定乾坤