【Redis】Redis的淘汰策略

Redis的内存淘汰

当Redis的实际使用内存超出Redis配置参数maxmemory后,Redis会根据配置来决定如何腾出新的空间来继续提供读写服务。

这和Reids的过期策略不一样,过期策略是设置了过期时间的key的删除策略,而内存淘汰是当内存溢出时发生的事件。

几种可选淘汰策略:

通过maxmemory-policy进行设置:

1、noeviction(默认):写请求不可用,读请求可用(del指令也可用),保证了数据不丢失,但线上业务不可持续进行。

2、volatile-lru:尝试淘汰设置了过期时间的key,而且最少使用的key被淘汰。没有设置过期时间的key不会被淘汰,这保证了需要持久化的数据不会突然丢失。

3、volatile-ttl:尝试淘汰设置了过期时间的key,比较key的剩余寿命ttl的值,越小的优先淘汰。
【Redis】Redis的淘汰策略_第1张图片

4、volatile-random:尝试淘汰设置了过期时间的key,随机选择设置了过期时间的key进行淘汰。

5、allkeys-lru:全体key中最少使用的key被淘汰(不管有没有设置过期时间)

6、allkeys-random:全体key中随机淘汰。

总结一下,volatile-类型的策略只选择设置了过期时间的key根据一定算法进行淘汰,allkeys-类型策略对所有key进行淘汰。

LRU算法

底层大概就是一个双向链表+key/value字典,链表元素被使用的顺序进行排列(某个元素被访问后,会移动到链表头部,所以链表元素排列顺序就是元素最近被使用的时间顺序)。

这样位于链表尾部的元素就是最近最少使用的元素(当然不排除这个链表所有key被使用率都很高),这样进行删除操作时,只需要对链表尾部元素进行删除(O(1))就可以了。

Redis的近似LRU算法

Redis给每个key增加了一个额外的字段,这个字段长度为24bit,存储的是这个key的最后一次被访问的时间戳。

需要注意的是,Redis的LRU淘汰采用的是懒惰处理。也就是只有当Redis执行写操作时,发现内存超出maxmemory,就会执行一次LRU淘汰算法(随机选出5个key(maxmemory-samples设置),然后淘汰最少使用的key。如果进行淘汰后,还是超出maxmemory,再次进行随机淘汰)。

Redis3.0后增加了淘汰池:一个数组,大小为maxmemory-samples,每一次淘汰循环中,新的随机得出的key列表会和淘汰池的key列表进行融合,淘汰最少使用的一个key后,保留剩余的key列表放入淘汰池中等待下一个淘汰循环。

你可能感兴趣的:(Redis)