大约阅读4分钟,写于 2021 0408 22:33 床前书桌台灯下
redis
若是你使用过 redis,那你必定知道过时策略这个命令吧,若是让你设计一个过时键接口,你有什么想法?数据库
咱们在使用 redis 时,通常会设置一个过时时间,固然也有不设置过时时间的,也就是永久不过时。缓存
当咱们设置了过时时间,redis 是如何判断是否过时,以及根据什么策略来进行删除的。服务器
redis 设置过时时间:expire key time
(以秒为单位) – 这是最经常使用的方式setex(String key, int seconds, String value)
– 字符串独有的方式markdown
除了字符串本身独有设置过时时间的方法外,其余方法都须要依靠 expire
方法来设置时间并发
若是没有设置时间,那缓存就是永不过时ide
若是设置了过时时间,以后又想让缓存永不过时,使用 persist key
memcached
三种过时策略:性能
目录:
atom
含义:在设置 key 的过时时间的同时,为该 key 建立一个定时器,让定时器在 key 的过时时间来临时,对 key 进行删除
优势:保证内存被尽快释放
缺点:若过时 key 不少,删除这些 key 会占用不少的 CPU 时间,在 CPU 时间紧张的状况下, CPU 不能把全部的时间用来作要紧的事儿,还须要去花时间删除这些 key,定时器的建立耗时,若为每个设置过时时间的 key 建立一个定时器(将会有大量的定时器产生),性能影响严重。
懒汉式删除流程:
对于按期删除,在程序中有一个全局变量 current_db
来记录下一个将要遍历的库,假设有 16 个库,咱们这一次按期删除遍历了 10 个,那此时的 current_db
就是 11,下一次按期删除就从第11个库开始遍历,假设 current_db
等于 15 了,那么以后遍历就再从 0 号库开始(此时 current_db==0)
在实际中,若是咱们要本身设计过时策略, 在使用 懒汉式删除+按期删除
时,控制时长和频率这个尤其关键,须要结合服务器性能,以及并发量等状况进行调整,以至最佳。
Redis 有四个不一样的命令能够用于设置键的生存时间(键能够存在多久)或过时时间(键何时会被删除):
EXPIRE<key><ttl>
命令用于将键 key 的生存时间设置为 ttl 秒。
PEXPIRE<key><ttl>
命令用于将键 key 的生存时间设置为 ttl 毫秒。
EXPIREAT<key><timestamp>
命令用于将键 key 的过时时间设置为 timestamp 所指定的秒数时间戳。
PEXPIREAT<key><timestamp>
命令用于将键 key 的过时时间设置为 timestamp 所指定的毫秒数时间戳。
原理:
虽然有多种不一样单位和不一样形式的设置命令,但实际上 EXPIRE、PEXPIRE、EXPIREAT
三个命令都是使用PEXPIREAT
命令来实现的:不管客户端执行的是以上四个命令中的哪个,通过转换以后,最终的执行效果都和执行 PEXPIREAT
命令同样。
redisDb 结构的 expires 字典保存了数据库中全部键的过时时间,咱们称这个字典为过时字典
过时字典的键是一个指针,这个指针指向键空间中的某个键对象(也便是某个数据库键)。
过时字典的值是一个 long long 类型的整数,这个整数保存了键所指向的数据库键的过时时间——一个毫秒精度的 UNIX 时间戳。
下图展现了一个带有过时字典的数据库例子,在这个例子中,键空间保存了数据库中的全部键值对,而过时字典则保存了数据库键的过时时间。
为了展现方便,图中的键空间和过时字典中重复出现了两次 alphabet 键对象和 book 键对象。在实际中,键空间的键和过时字典的键都指向同一个键对象,因此不会出现任何重复对象,也不会浪费任何空间。
图中的过时字典保存了两个键值对:
第一个键值对的键为 alphabet 键对象,值为1385877600000,这表示数据库键 alphabet 的过时时间为1385877600000(2013年12月1日零时)。
第二个键值对的键为 book 键对象,值为 1388556000000,这表示数据库键 book 的过时时间为1388556000000(2014年1月1日零时)。当客户端执行 PEXPIREAT 命令(或者其余三个会转换成 PEXPIREAT 命令的命令)为一个数据库键设置过时时间时,服务器会在数据库的过时字典中关联给定的数据库键和过时时间。
在服务器执行如下命令以后
过时字典将新增一个键值对,其中键为 message 键对象,而值则为 1391234400000(2014年2月1日零时),如图:
如下是 PEXPIREAT 命令的伪代码定义
PERSIST 命令能够移除一个键的过时时间
PERSIST 命令就是 PEXPIREAT 命令的反操做:PERSIST 命令在过时字典中查找给定的键,并解除键和值(过时时间)在过时字典中的关联。
过时键的断定
经过过时字典,程序能够用如下步骤检查一个给定键是否过时: