常见的删除策略

1.定时删除:在设置键的过期时间的同时,创建一个timer,让定时器在键的过期时间到达时,立即执行对键的删除操作。(主动删除)

对内存友好,但是对cpu时间不友好,有较多过期键的而情况下,删除过期键会占用相当一部分cpu时间。

2.惰性删除:放任过期键不管,但是每次从键空间中获取键时,都检查取到的键是否过去,如果过期就删除,如果没过期就返回该键。(被动删除)

对cpu时间友好,程序只会在取出键的时候才会对键进行过期检查,这不会在删除其他无关过期键上花费任何cpu时间,但是如果一个键已经过期,而这个键又保留在数据库中,那么只要这个过期键不被删除,他所占用的内存就不会释放,对内存不友好。

3.定期删除:每隔一段时间就对数据库进行一次检查,删除里面的过期键。(主动删除)

采用对内存和cpu时间折中的方法,每个一段时间执行一次删除过期键操作,并通过限制操作执行的时长和频率来减少对cpu时间的影响。难点在于,选择一个好的策略来设置删除操作的时长和执行频率。

redis使用的过期策略:定期删除+惰性删除

定期删除

redis 会将每个设置了过期时间的 key 放入到一个独立的字典中,以后会定期遍历这个字典来删除到期的 key。

Redis 默认会每秒进行十次过期扫描(100ms一次),过期扫描不会遍历过期字典中所有的 key,而是采用了一种简单的贪心策略。

  • 从过期字典中随机 20 个 key;
  • 删除这 20 个 key 中已经过期的 key;
  • 如果过期的 key 比率超过 1/4,那就重复步骤 1;

redis默认是每隔 100ms就随机抽取一些设置了过期时间的key,检查其是否过期,如果过期就删除。注意这里是随机抽取的。为什么要随机呢?你想一想假如 redis 存了几十万个 key ,每隔100ms就遍历所有的设置过期时间的 key 的话,就会给 CPU 带来很大的负载!

惰性删除

所谓惰性策略就是在客户端访问这个key的时候,redis对key的过期时间进行检查,如果过期了就立即删除,不会给你返回任何东西。

定期删除可能会导致很多过期key到了时间并没有被删除掉。所以就有了惰性删除。假如你的过期 key,靠定期删除没有被删除掉,还停留在内存里,除非你的系统去查一下那个 key,才会被redis给删除掉。这就是所谓的惰性删除,即当你主动去查过期的key时,如果发现key过期了,就立即进行删除,不返回任何东西.

定期删除是集中处理,惰性删除是零散处理。

为什么要采用定期删除+惰性删除2种策略呢?

如果过期就删除。假设redis里放了10万个key,都设置了过期时间,你每隔几百毫秒,就检查10万个key,那redis基本上就死了,cpu负载会很高的,消耗在你的检查过期key上了.

但是问题是,定期删除可能会导致很多过期key到了时间并没有被删除掉,那咋整呢?所以就是惰性删除了。这就是说,在你获取某个key的时候,redis会检查一下 ,这个key如果设置了过期时间那么是否过期了?如果过期了此时就会删除,不会给你返回任何东西。

并不是key到时间就被删除掉,而是你查询这个key的时候,redis再懒惰的检查一下

通过上述两种手段结合起来,保证过期的key一定会被干掉。

所以说用了上述2种策略后,下面这种现象就不难解释了:数据明明都过期了,但是还占有着内存

redis内存淘汰机制

但是仅仅通过设置过期时间还是有问题的。我们想一下:如果定期删除漏掉了很多过期 key,然后你也没及时去查,也就没走惰性删除,此时会怎么样?如果大量过期key堆积在内存里,导致redis内存快耗尽了。redis是如何解决这个问题呢? 使用redis 内存淘汰机制

这个问题可能有小伙伴们遇到过,放到Redis中的数据怎么没了?

因为Redis将数据放到内存中,内存是有限的,比如redis就只能用10个G,你要是往里面写了20个G的数据,会咋办?当然会干掉10个G的数据,然后就保留10个G的数据了。那干掉哪些数据?保留哪些数据?当然是干掉不常用的数据,保留常用的数据了

redis 提供 6种数据淘汰策略:

  • no-eviction:不会继续服务写请求(DEL请求可以继续服务),读请求可以继续进行。这样可以保证不会丢失数据,但是会让线上的业务不能持续进行。这是默认的淘汰策略。
  • volatile-lru:尝试淘汰设置了过期时间的 key,最少使用的 key 优先被淘汰。没有设置过期时间的key不会被淘汰,这样可以保证需要持久化的数据不会突然丢失。(这个是使用最多的)
  • volatile-ttl:跟上面一样,除了淘汰的策略不是 LRU,而是 key 的剩余寿命 ttl 的值,ttl 越小越优先被淘汰,即淘汰将要过期的数据.
  • volatile-random:从已设置过期时间的数据集(server.db[i].expires)中随机选择数据淘汰
  • allkeys-lru:区别于 volatile-lru,这个策略要淘汰的 key 对象是全体的 key 集合,而不只是过期的 key 集合。这意味着没有设置过期时间的 key 也会被淘汰。
  • allkeys-random:从全体的key集合(server.db[i].dict)中任意选择数据淘汰
配置方式:
maxmemory-policy volatile-lru #默认是noeviction,即不进行数据淘汰

redis过期策略和内存淘汰机制的更多相关文章

  1. Redis(六)--- Redis过期策略与内存淘汰机制

    1.简述 关于Redis键的过期策略,首先要了解两种时间的区别,生存时间和过期时间: 生存时间:一段时长,如30秒.6000毫秒,设置键的生存时间就是设置这个键可以存在多长时间,命令有两个 expir ...

  2. redis过期策略与内存淘汰机制分析

    过期策略: 我们在set key时,可以给一个expire time,就是过期时间 这段过期时间以后,redis对key删除使用:定期删除+惰性删除 定期删除指redis默认在100ms内随机抽取一些 ...

  3. redis过期策略以及内存淘汰机制(理论+配置)

    一.redis的过期策略: redis的过期策略是:定期删除+惰性删除redis在存储数据时,可能会设置过期时间,而所谓的定期删除,指的是redis默认是每隔100ms就随机抽取一些设置了过期时间的k ...

  4. redis过期策略、内存淘汰策略、持久化方式、主从复制

    原文链接:https://blog.csdn.net/a745233700/article/details/85413179 一.Redis的过期策略以及内存淘汰策略:1.过期策略:定期删除+惰性删除 ...

  5. Redis的过期策略和内存淘汰机制

    过期策略 我们set key的时候,都可以给一个expire time,就是过期时间,指定这个key比如说只能存活1个小时,我们自己可以指定缓存到期就失效. 如果假设你设置一个一批key只能存活1个小 ...

  6. redis的过期策略以及内存淘汰机制

    redis采用的是定期删除+惰性删除策略. 为什么不用定时删除策略? 定时删除,用一个定时器来负责监视key,过期则自动删除.虽然内存及时释放,但是十分消耗CPU资源.在大并发请求下,CPU要将时间应 ...

  7. 关于redis的几件小事(四)redis的过期策略以及内存淘汰机制

    1.数据为什么会过期? 首先,要明白redis是用来做数据缓存的,不是用来做数据存储的(当然也可以当数据库用),所以数据时候过期的,过期的数据就不见了,过期主要有两种情况, ①在设置缓存数据时制定了过 ...

  8. Redis的过期删除策略(和内存淘汰机制)-转

    版权声明:本文为CSDN博主「奥修诺斯」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明.原文链接:https://blog.csdn.net/qq_39944869/ ...

  9. Redis 中的过期删除策略和内存淘汰机制

    Redis 中 key 的过期删除策略 前言 Redis 中 key 的过期删除策略 1.定时删除 2.惰性删除 3.定期删除 Redis 中过期删除策略 从库是否会脏读主库创建的过期键 内存淘汰机制 ...

随机推荐

  1. MySQL Docker方式安装

    以5.7版本为例 1 配置mysql配置文件编辑/etc/my.cnf,添加以下内容: [mysqld] skip-host-cache skip-name-resolve datadir=/var/ ...

  2. Shock wave

    ** shock wave thickness of shock wave is order of 1e-7 m why governed by Euler Equation? P334 shock ...

  3. JavaSE 学习笔记之正则表达式(二十五)

    正则表达式:其实是用来操作字符串的一些规则. 好处:正则的出现,对字符串的复杂操作变得更为简单. 特点:将对字符串操作的代码用一些符号来表示.只要使用了指定符号,就可以调用底层的代码对字符串进行操作. ...

  4. vue.js中的路由vue-router2.0使用

    在我们平时工作中,我们有时候会有需求,按照不同的规则,加载不同的组件,页面不去跳转,常见的操作是ajax的异步操作,实现局部刷新加载新数据 在vue中,我们写了很多不同的组件,这时候,实现不刷新调用新 ...

  5. nyoj_79_拦截导弹_201403182040

    拦截导弹 时间限制:3000 ms  |  内存限制:65535 KB 难度:3   描述 某国为了防御敌国的导弹袭击,发展中一种导弹拦截系统.但是这种导弹拦截系统有一个缺陷:虽然它的第一发炮弹能够到 ...

  6. JAVA内存模型与线程以及volatile理解

    Java内存模型是围绕在并发过程中如何处理原子性.可见性.有序性来建立的. 一.主内存与工作内存 Java内存模型主要目标是在虚拟机中将变量存储到内存和从内存中取出变量.这里的变量包括:实例字段.静态 ...

  7. [bzoj3809]Gty的二逼妹子序列_莫队_分块

    Gty的二逼妹子序列 bzoj-3809 题目大意:给定一个n个正整数的序列,m次询问.每次询问一个区间$l_i$到$r_i$中,权值在$a_i$到$b_i$之间的数有多少个. 注释:$1\le n\ ...

  8. UVA_1575

    https://vjudge.net/problem/UVA-1575 枚举答案(k)..对k质因数分解,质数的指数为cnt[i],若n==A(tot_cnt,tot_cnt) / A(cnt[i]& ...

  9. PHP小白学习日程之旅

    我是一名专升本的学生,在这里偶然接触了博客园,我觉得非常好,每天可以在这里看别人的分享与学习,还会在大学学习俩年,我只想专注的吧自己的技术提高,跟园子里的朋友们一起学习与分享加油!!!!!!!!!!! ...

  10. 字段not null属性要放在最后面写,最少在类型后面写

    报错:create table test2211(id not null bigint ,age timestamp); 正确写法:create table test2211(id bigint no ...