Redis的介绍以及基本原理

Redis 是一款高性能的内存数据库,凭借其内存存储和单线程架构实现快速读写。它提供了RDB和AOF两种持久化方式确保数据安全,RDB在特定条件触发保存数据快照,AOF记录所有写操作并在重启时回放。Redis的主从复制为分布式和集群奠定了基础。在面临持久化带来的性能挑战时,如fork操作和AOF追加阻塞,可以通过调整策略和硬件优化来解决。
摘要由CSDN通过智能技术生成

Redis的介绍

  Redis是一种基于键值对的Nosql数据库,由于其所有的数据都存放在内存中,所以它的读写性能非常的惊人

一、Redis的特性
速度快
原因一:其数据在内存中存储
原因二:采用c语言实现
原因三:采用单线程架构,避免了多线程频繁的内存切换


基于键值对的数据结构服务器
  主要提供了五种基本的数据结构:string、list、hash、set、zset


支持丰富的功能
提供键过期功能
提供消息发布订阅功能
提供了简单的事务功能
提供持久化功能
将数据放到内存中是不安全的,一旦发生断电或者机器故障,就会出现数据丢失的情况。redis 提供了两种持久化的方式 RDB 和 AOF。


主从复制
提供复制功能,复制功能是分布式的基础,主从复制是集群实现的基础。

二、Redis的持久化

redis支持RDB、AOF两种持久化机制。持久化机制能有效避免数据丢失问题。

1、RDB
RDB是将当前进程的数据的数据生成快照保存到硬盘的过程,RDB持久化过程分为手动触发和自动触发。

手动触发
(1)使用save 命令:阻塞当前redis服务器,直到RDB过程完成。可能会造成长时间的阻塞,不建议线上使用。
(2)使用bgsave命令:Redis执行fork操作,创建子进程,子进程用于持久化,完成后自动结束,阻塞只发生在fork阶段。
2. 被动触发
(1)使用save m n 相关配置,表示m秒内进行n次修改时,触发RDB操作。
(2)从节点执行全量复制操作
(3)执行debug reload 命令重新加载redis时,触发RDB
3. RDB的优缺点

优点
(1)采用rdf存储的为紧凑压缩的二进制文件,代表某个时间点上的数据快照。
(2)Redis加载RDB恢复数据远远快于AOF的方式。
缺点
(1)不能实时的持久化数据
(2)多个格式的RDB版本,存在不兼容的情况。
2.AOF(append only file)
以独立日志的方式记录每次写命令,重启的时候在重新执行AOF文件中的命令以达到恢复数据的目的。其解决了RDB中无法实时的持久化问题。目前是 Redis 主流的持久化方式。
这里需要注意:AOF写入的内容就是文本格式

数据同步策略
(1) always : 每写一条命令就同步一次
(2) everysec: 每秒同步一次(推荐使用)
(3) no: 有操作系统负责,周期最长为30秒

重写机制
随着命令不断的被写入AOF,文件会越来越大,为了解决这个问题,Redis引入重写机制用来压缩文件的体积。AOF文件重写机制就是将Redis进程中的数据转换为写命令同步到新的AOF文件中。
这里有个疑问:为什么重写机制可以保证压缩文件体积:(1)去掉了一些没用的命令,del (2) 对某些命令进行合并,lpush num a, lpush num b , lpush num b 可以合并成lpush num a b c (3) 还可能存在超时的键,不用存在AOF文件中

四、Redis问题
Redis持久化功能一直是影响Redis性能的高发地。

1.fork操作
无论是RDB还是AOF,都需要进行fork操作,对于操作系统来说,fork算是一个重量级操作。虽然fork操作不需要拷贝父进程的内存空间,但是会复制空间内存页表。
解决方案:控制redis实例最大可用内存,fork操作耗时和内存量成正比。

2.AOP追加阻塞
(1)使用everysec同步策略,最多丢失两秒的数据;

(2)如果系统的fsync比较慢,则会影响Redis主进程的性能。

解决方案:

(1)不要和其他高硬盘负载的服务部署在一起,存储服务、消息队列服务
(2)使用ssd硬盘

Redis基本原理

1.redis为啥会那么快?

 redis 时单线程的为什么还能那么快?

数据都在内存中,运算都是内存级别的运算。

redis既然是单线程的为什么能处理那么多的并发数?

多路复用,操作系统时间轮训epoll 函数作为选择器,维护了指令队列,和响应队列,java的nio。

select ,poll, epoll

rset ,fds(文件描述符的集合)。而select模型存储fds的方式是采取的bitmap,默认最大1024个。

2.执行流程

1.select模型每次都直接将rset(也就是fds)全部拷贝到内核态,因为内核态速度比用户空间态快很多。
2.如果没数据的话,select函数会阻塞,如果有数据的话会执行两步
(1)将有数据的那个fd置位(也就是标记一下,代表这个fd有数据)
(2)select函数不在阻塞,将继续往下执行。也就是整体遍历fds,找到有数据的那个fd读取数据做处理。他的fd不能重用,每一次都需要重新创建新的fds且将用户空间态的fds拷贝到内核态

3、缺点
fds最大支持1024个(可以更改,但是意义不大)
fd不可重用,每次内核态都给置位了,导致为了标记fd,必须创建一个新的rset从而导致fds在用户态内存态间多次拷贝(也就是fds)

用户控件态拷贝rset到内核态也需要时间,虽然内核态执行比用户态快,但是copy也需要开销
O(n)再次遍历问题。因为rset里的fd被置位后,select函数并不知道哪个被置位了,需要从头遍历到尾,逐个对比。

redis更多信息以及命令使用请查看官方文档,后续将会对使用命令进行详细探析,下面是redis的官网

http://www.redis.cn/commands.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值