Redis中的事务、过期数据清除策略、LRU和LFU算法以及数据持久化

事务

概念:

通常我们提及数据库都不可避免的要提到事务,那么什么是事务呢?事务是指作为单个逻辑工作单元执行的一系列操作。所以,首先事务是一系列操作,这一系列操作具有二态性,即完全地执行或者完全地不执行。因此事务处理可以确保除非事务单元内的所有操作的成功完成,否则不会想数据库更新面向数据的资源。我们这里举一个例子,数据库中除查询操作(Select)以外,插入(Insert)、删除(Delete)和更新(Update)这三种操作都会对数据造成影响,因为事务处理能够保证一系列操作可以完全地执行或者完全不执行,因此在一个事务被提交以后,该事务中的任何一条SQL语句在被执行的时候,都会生成一条撤销日志(Undo Log),而撤销日志中记录的是和当前擦作完全相反的操作,比如删除的相反操作是插入,插入的相反操作是删除等。我们通常所说的事务回滚其实就是去执行这些插销日志里的相反操作,这同样告诉我们一个道理,只有事务中的一系列操作完全执行的情况下可以回滚,如果是在意外情况下导致事务中的一系列操作没有完全执行,这个时候我们是不能保证数据一定可以回滚的。

​ 在数据库相关理论中,一个逻辑工作单元想要成为事务,就必须满足ACID,即原子性、一致性、隔离性和持久性。

(1)原子性:原子性这个概念其实就是指,一个事务内的所有SQL操作都是一个整体,因此只有所有的SQL操作都完全执行成功,该事务方可以认为提交成功。如果在提交事务过程中某一条SQL语句执行失败,则整个事务必须回滚到事务提交前的状态。
(2)一致性:而一致性这个概念则是指,事务在完成的时候,必须要保证所有的数据都保持一致的状态,而落实到数据库的各个组成部分上,则要求开发人员能够保证数据、索引、约束、日志等在事务前后具备一致性。
(3)隔离性:隔离性这个概念主要针对并发,其核心思想就是不同的并发事务对数据产生的修改必须是相互隔离的,假设有两个不同的事务A和B并发执行,那么对A来讲,它在执行前的状态只有两种,即B执行前和B执行后。同理,对B来讲同样是如此,这样的特性我们就称为隔离性。
(4)持久性:持久性相对简单,是指事务完成以后它对数据的影响是永久性的。

举例:

myredis:0>multi

"OK"
myredis:0>set name g1

"QUEUED"
myredis:0>set name g2

"QUEUED"
myredis:0>set name g3

"QUEUED"
myredis:0>get name

"QUEUED"
myredis:0>exec

1) "OK"

2) "OK"

3) "OK"

4) "OK"

5) "OK"

6) "OK"

7) "OK"

8) "g3"

9) "OK"
myredis:0>

过期数据清除策略

redis有固定的存储空间 可以通过:

CONFIG SET maxmemory 4gb

命令来设置大小(此处设为4gb)

有固定存储空间,就意味着,数据会有存满的时候,那么当数据存满时,多余的数据应该如何处理呢?处理哪些数据,以及怎样处理数据?

一、redis的过期清除策略

有两种:定期清除+惰性删除。定期清除是指 redis会定期随机挑选一些key,检查其是否过期,如果过期,则清除。惰性删除是指,在用户要查看key时,redis会检查一下这个key是否过期,如果过期,则清除。这样的话,则存在一种情况,就是缓存既没有被用户使用,也没有被随机挑选到,那么这样的缓存就会一直堆积在内存中无法被清除。此时就需要引入redis的缓存淘汰策略:

二、redis的缓存淘汰策略

noeviction 不进行缓存淘汰,存满以后拒绝继续存。
volatile-ttl 在即将过期的键值对中,移除即将过期的键值对
volatile-random 在即将过期的键值对,随机移除键值对
volatile-lru:在设置了过期时间的键值对中,移除最近最少使用的键值对。

volatile-lfu:在设置了过期时间的键值对中,移除最近最不频繁使用的键值对

allkeys-random:在所有键值对中,随机移除某个key。

allkeys-lru:在所有的键值对中,移除最近最少使用的键值对。

allkeys-lfu:在所有的键值对中,移除最近最不频繁使用的键值对

LRU和LFU算法

1.LRU算法:

原生LRU算法:

维护一条链表,最常使用的放最右,最不常用的放最左。新元素进入时,从MRU端进入,相应的剔除一个LRU端的元素。

在这里插入图片描述

数据量大时,存在性能问题,redis要一直维护一条链表的增删元素。所以redis对此算法做了优化。

优化LRU算法:

在“链表”与“增删元素”直接加了一层缓存。以元素最近被访问的一次时间t作为判定标准,把符合标准的元素单独存到一个缓存中,需要删除元素,则从缓存中取t最早的元素删除。来提高效率。

2.LFU算法:

计算出元素的使用频率,来作为评判“是否该被淘汰”的标准。

核心就是访问次数越大,访问次数被递增的可能性越小,最大 255,可以在配置 redis.conf 中写明访问多少次递增多少。由于访问次数是有限的,直接一个255数组或链表都可以。

16bit 部分保存的是时间戳的后16位(分钟),表示上一次递减的时间,算法是这样执行,随机采样N个key,检查递减时间,如果距离现在超过 N 分钟(可配置),则递减或者减半(如果访问次数数值比较大)。

此外,由于新加入的 key 访问次数很可能比不被访问的老 key小,为了不被马上淘汰,新key访问次数设为 5。

数据持久化

redis是一个内存数据库,数据保存在内存中,而内存的数据变化是很快的,也容易发生丢失。所以Redis为用户提供了持久化的机制,分别是RDB(RedisDataBase)和AOF(AppendOnlyFile)。

redis的持久化流程:

客户端向服务端发送写操作(数据在客户端的内存中)
数据库服务端接收到写请求的数据(数据在服务端的内存中)
服务端调用write这个系统调用,将数据往磁盘上写(数据在系统内存的缓冲区中)
操作系统将缓冲区中的数据转移到磁盘控制器上(数据在磁盘缓存中)
磁盘控制器将数据写到磁盘的物理介质中(数据真正落到磁盘上)
关于redis如何来实现上面5个保存到磁盘的步骤,它提供了两种策略机制,也就是RDB和AOF

RDB机制:

RDB持久化就是把指定时间间隔内的数据以快照的形式持久化到磁盘,写入到二进制文件中,默认为dump.rdb。(redis所有的配置都是在redis.conf文件中,里面包括了RDB和AOF两种持久化机制的各种配置),对于RDB来说,有三种触发机制:save、bgsave和自动化。save会阻塞redis服务器,不可取;bgsave为异步进行持久化,可取;自动化为通过配置redis.conf的方式实现自动持久化、机制为bgsave。

RDB机制的劣势:

当进行快照持久化时,会开启一个子进程专门负责快照持久化,子进程会拥有父进程的内存数据,父进程修改内存子进程不会同步,所以在快照持久化期间修改的数据不会被保存,可能丢失数据。

AOF机制:

全量备份总是耗时的,所以redis提供了一种更加高效的方式AOF,工作机制很简单,redis会将每一个收到的写命令都通过write函数追加到文件中。通俗的理解就是日志记录。记录的日志存入aof文件中,但随着时间累计,aof文件会越变越大,redis还提供了一种bgrewriteaof命令重写aof文件,重写aof文件的操作,并没有读取旧的aof文件,而是将整个内存中的数据库内容用命令的方式重写了一个新的aof文件,这点和快照有点类似。AOF有三种触发机制:每次修改都同步;每秒同步一次;从不同步。

AOF机制的劣势:

AOF文件通常比RDB文件更大;支持的写QPS比RDB支持的写QPS低;曾有过没有恢复出原始数据的bug。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值