Redis详解(十一)------ 过期删除策略和内存淘汰策略
在介绍这篇文章之前,我们先来看如下几个问题:
①、如何设置Redis键的过期时间?
②、设置完一个键的过期时间后,到了这个时间,这个键还能获取到么?假如获取不到那这个键还占据着内存吗?
③、如何设置Redis的内存大小?当内存满了之后,Redis有哪些内存淘汰策略?我们又该如何选择?
如果上面的几个问题你都懂,那么下面的内容你就不用看了;如果你不是很懂,那就带着这些问题往下看。
1、设置Redis键过期时间
Redis提供了四个命令来设置过期时间(生存时间)。
①、EXPIRE <key> <ttl> :表示将键 key 的生存时间设置为 ttl 秒。
②、PEXPIRE <key> <ttl> :表示将键 key 的生存时间设置为 ttl 毫秒。
③、EXPIREAT <key> <timestamp> :表示将键 key 的生存时间设置为 timestamp 所指定的秒数时间戳。
④、PEXPIREAT <key> <timestamp> :表示将键 key 的生存时间设置为 timestamp 所指定的毫秒数时间戳。
PS:在Redis内部实现中,前面三个设置过期时间的命令最后都会转换成最后一个PEXPIREAT 命令来完成。
另外补充两个知识点:
一、移除键的过期时间
PERSIST <key> :表示将key的过期时间移除。
二、返回键的剩余生存时间
TTL <key> :以秒的单位返回键 key 的剩余生存时间。
PTTL <key> :以毫秒的单位返回键 key 的剩余生存时间。
2、Redis过期时间的判定
在Redis内部,每当我们设置一个键的过期时间时,Redis就会将该键带上过期时间存放到一个过期字典中。当我们查询一个键时,Redis便首先检查该键是否存在过期字典中,如果存在,那就获取其过期时间。然后将过期时间和当前系统时间进行比对,比系统时间大,那就没有过期;反之判定该键过期。
3、过期删除策略
通常删除某个key,我们有如下三种方式进行处理。
①、定时删除
在设置某个key 的过期时间同时,我们创建一个定时器,让定时器在该过期时间到来时,立即执行对其进行删除的操作。
优点:定时删除对内存是最友好的,能够保存内存的key一旦过期就能立即从内存中删除。
缺点:对CPU最不友好,在过期键比较多的时候,删除过期键会占用一部分 CPU 时间,对服务器的响应时间和吞吐量造成影响。
②、惰性删除
设置该key 过期时间后,我们不去管它,当需要该key时,我们在检查其是否过期,如果过期,我们就删掉它,反之返回该key。
优点:对 CPU友好,我们只会在使用该键时才会进行过期检查,对于很多用不到的key不用浪费时间进行过期检查。
缺点:对内存不友好,如果一个键已经过期,但是一直没有使用,那么该键就会一直存在内存中,如果数据库中有很多这种使用不到的过期键,这些键便永远不会被删除,内存永远不会释放。从而造成内存泄漏。
③、定期删除
每隔一段时间,我们就对一些key进行检查,删除里面过期的key。
优点:可以通过限制删除操作执行的时长和频率来减少删除操作对 CPU 的影响。另外定期删除,也能有效释放过期键占用的内存。
缺点:难以确定删除操作执行的时长和频率。
如果执行的太频繁,定期删除策略变得和定时删除策略一样,对CPU不友好。
如果执行的太少,那又和惰性删除一样了,过期键占用的内存不会及时得到释放。
另外最重要的是,在获取某个键时,如果某个键的过期时间已经到了,但是还没执行定期删除,那么就会返回这个键的值,这是业务不能忍受的错误。
4、Redis过期删除策略
前面讨论了删除过期键的三种策略,发现单一使用某一策略都不能满足实际需求,聪明的你可能想到了,既然单一策略不能满足,那就组合来使用吧。
没错,Redis的过期删除策略就是:惰性删除和定期删除两种策略配合使用。
惰性删除:Redis的惰性删除策略由 db.c/expireIfNeeded 函数实现,所有键读写命令执行之前都会调用 expireIfNeeded 函数对其进行检查,如果过期,则删除该键,然后执行键不存在的操作;未过期则不作操作,继续执行原有的命令。
定期删除:由redis.c/activeExpireCycle 函数实现,函数以一定的频率运行,每次运行时,都从一定数量的数据库中取出一定数量的随机键进行检查,并删除其中的过期键。
注意:并不是一次运行就检查所有的库,所有的键,而是随机检查一定数量的键。
定期删除函数的运行频率,在Redis2.6版本中,规定每秒运行10次,大概100ms运行一次。在Redis2.8版本后,可以通过修改配置文件redis.conf 的 hz 选项来调整这个次数。
看上面对这个参数的解释,建议不要将这个值设置超过 100,否则会对CPU造成比较大的压力。
我们看到,通过过期删除策略,对于某些永远使用不到的键,并且多次定期删除也没选定到并删除,那么这些键同样会一直驻留在内存中,又或者在Redis中存入了大量的键,这些操作可能会导致Redis内存不够用,这时候就需要Redis的内存淘汰策略了。
5、内存淘汰策略
①、设置Redis最大内存
在配置文件redis.conf 中,可以通过参数 maxmemory <bytes> 来设定最大内存:
不设定该参数默认是无限制的,但是通常会设定其为物理内存的四分之三。(这里有个疑惑:为啥作者不考虑将此参数设定为百分比呢?)
②、设置内存淘汰方式
当现有内存大于 maxmemory 时,便会触发redis主动淘汰内存方式,通过设置 maxmory-policy ,有如下几种淘汰方式:
1)volatile-lru 利用LRU算法移除设置过过期时间的key (LRU:最近使用 Least Recently Used ) 。
2)allkeys-lru 利用LRU算法移除任何key (和上一个相比,删除的key包括设置过期时间和不设置过期时间的)。通常使用该方式。
3)volatile-random 移除设置过过期时间的随机key 。
4)allkeys-random 无差别的随机移除。
5)volatile-ttl 移除即将过期的key(minor TTL)
6)noeviction 不移除任何key,只是返回一个写错误 ,默认选项,一般不会选用。
在redis.conf 配置文件中,可以设置淘汰方式:
6、总结
通过上面的介绍,相信大家对Redis的过期数据删除策略和内存淘汰策略有一定的了解了。这里总结一下:
Redis过期删除策略是采用惰性删除和定期删除这两种方式组合进行的,惰性删除能够保证过期的数据我们在获取时一定获取不到,而定期删除设置合适的频率,则可以保证无效的数据及时得到释放,而不会一直占用内存数据。
但是我们说Redis是部署在物理机上的,内存不可能无限扩充的,当内存达到我们设定的界限后,便自动触发Redis内存淘汰策略,而具体的策略方式要根据实际业务情况进行选取。
Redis详解(十一)------ 过期删除策略和内存淘汰策略的更多相关文章
- 【Redis】过期键删除策略和内存淘汰策略
Redis 过期键策略和内存淘汰策略 目录 Redis 过期键策略和内存淘汰策略 设置Redis键过期时间 Redis过期时间的判定 过期键删除策略 定时删除 惰性删除 定期删除 Redis过期删除策 ...
- 面试官:Redis 过期删除策略和内存淘汰策略有什么区别?
作者:小林coding 计算机八股文网站:https://xiaolincoding.com 大家好,我是小林. Redis 的「内存淘汰策略」和「过期删除策略」,很多小伙伴容易混淆,这两个机制虽然都 ...
- redis过期策略、内存淘汰策略、持久化方式、主从复制
原文链接:https://blog.csdn.net/a745233700/article/details/85413179 一.Redis的过期策略以及内存淘汰策略:1.过期策略:定期删除+惰性删除 ...
- Redis的过期策略和内存淘汰策略(转)
Redis的过期策略 我们都知道,Redis是key-value数据库,我们可以设置Redis中缓存的key的过期时间.Redis的过期策略就是指当Redis中缓存的key过期了,Redis如何处理. ...
- Redis的过期策略和内存淘汰策略
Redis的过期策略:通常有三种,Redis中同时使用惰性过期和定期过期两种过期策略组合. 定时过期:每个设置过期时间的key都需要创建一个定时器,到过期时间就会立即清除.该策略可以立即清除过期的数据 ...
- redis键的过期和内存淘汰策略
键的过期时间 设置过期时间 Redis可以为存储在数据库中的值设置过期时间,作为一个缓存数据库,这个特性是很有帮助的.我们项目中的token或其他登录信息,尤其是短信验证码都是有时间限制的. 按照传统 ...
- Redis详解(四)——删除策略
Redis详解(四)--删除策略 Redis中的数据特征 Redis是一种内存级数据库,所有数据均存放在内存中,内存中的数据可以通过TTL指令来获取其状态,当 key 不存在时,返回 -2 . 当 k ...
- Redis 中的过期删除策略和内存淘汰机制
Redis 中 key 的过期删除策略 前言 Redis 中 key 的过期删除策略 1.定时删除 2.惰性删除 3.定期删除 Redis 中过期删除策略 从库是否会脏读主库创建的过期键 内存淘汰机制 ...
- Redis 键的过期删除策略及缓存淘汰策略
前言 Redis缓存淘汰策略与Redis键的过期删除策略并不完全相同,前者是在Redis内存使用超过一定值的时候(一般这个值可以配置)使用的淘汰策略:而后者是通过定期删除+惰性删除两者结合的方式进行内 ...
随机推荐
- 【Spark】快来学习RDD的创建以及操作方式吧!
目录 RDD的创建 三种方式 从一个集合中创建 从文件中创建 从其他的RDD转化而来 RDD编程常用API 算子分类 Transformation 概述 帮助文档 常用Transformation表 ...
- Java 多线程启动为什么调用 start() 方法而不是 run() 方法?
多线程在工作中多多少少会用到,我们知道启动多线程调用的是 start() 方法,而不是 run() 方法,你知道原因吗? 在探讨这个问题之前,我们先来了解一些多线程的基础知识~ 线程的状态 Java ...
- spring源码解析--上
本文是作者原创,版权归作者所有.若要转载,请注明出处. 首先是配置类 package com.lusai.config; import org.springframework.context.anno ...
- 存储过程——异常捕获&打印异常信息
目录 0. 背景说明 1. 建立异常信息表ErrorLog 2. 建立保存异常信息的存储过程 3. 建立在SQL Server中打印异常信息的存储过程 4. 建立一个用于测试的存储过程抛出异常进行测试 ...
- python语法学习第六天--字典
字典:可变容器类型,用键值对的形式采用花括号储存(键唯一) 语法:d={key1:value1,key2:value2} 访问字典中的值: 字典名[键名]#若字典中不存在则报错 更改字典: 添加值:字 ...
- [hdu1079]简单博弈
题意:两个人玩游戏,给定一个日期,他们轮流选择日期,可以选择当前日期的下一天,如果下一个月也有这一天的话则也可以选择下一个月的这一天.超过某一日期的人输. 思路:以天为状态,则一共有300多万个左右的 ...
- Jmeter-Throughput Controller 吞吐量控制器
比如在压测是时候,我设置了100个线程组,循环2次,那么我想根据吞吐量进行并发请求,这时候可以用到这个吞吐量控制器 PercentExecutions:按执行次数的百分比来计算执行次数,Through ...
- 05JAVA基础方法
一.格式 函数有返回值 public static 返回类型 方法名(参数类型 形参1,参数类型 形参2){ 函数体; return 返回值;//返回值必须是定义的返回类型 } 函数没有有返回值 pu ...
- SpringBoot2.0 @Cacheable 添加超时策略
SpringBoot2.0 @Cacheable 添加超时策略 逻辑比较简单,废话不多说,直接进入正题: 需求:SpringBoot 利用注解使缓存支持过期时间 (同@Cacheable @Cache ...
- 数学分析新讲(1) NOTE
前言:无聊才翻翻看看来复习啦..所以慢更(●'◡'●) 1.利用求和公式的性质推导: \[\sum^{n}_{k=1}k=n \] \[\sum^{n}_{k=1}k^2=\frac{n(n+1)(2 ...