Redis知识总结

388 阅读6分钟
      redis是基于内存,常用作缓存的一种技术,存储方式以key-value形式,但是内部实现数据结构是hash表,每创建一个数据时,分别创建两个hash数据,保存key与value,key一定为字符串
      优点:速度快,性能优越,支持多种数据结构
      缺点:受物理内存限制,不能用做海量数据保存,适合利用自身内存淘汰机制保留热点数据

redis基本数据类型

1.String字符串

      字符串类型可用来保存字符、整型、浮点型数据。

      基本命令

  • get key --获取值
  • set key value (expire) --设置值(有效期)
  • setnx key value --当存在该key时,返回0;不存在返回1,可用于实现分布式锁
  • del key -- 删除
  • incr key -- 递增
  • decr key -- 递减
  • strlen key -- 键长度

2. list(双向链表)

      栈:先进后出  队列:先进先出

  • lpush list value -- 从头部插入一条数据
  • rpush list value -- 从尾部插入一条数据
  • lpop list -- 从头部取出一条数据
  • rpop list -- 从底部取出一条数据
  • lrange list index1 index2 -- 遍历指针index1到index2到数据(0 -1时遍历所有数据)
  • lrem list index value -- 删除指针为index的值为value的数据

list可用于实现简单的消息队列,两种实现方式:

  1. lpush与rpop
  2. rpush与lpop

  3. set

      不存在重复元素,无顺序

  • sadd set value -- 往集合插入一条数据
  • srem set value -- 删除set集合中值为value的数据
  • smembers set -- 查询set集合中所有数据

      set还能查询两个集合中的交集、差集

 4. sorted set(有序集合)

      与set相似,不同的是每个元素可关联一个double类型的分数,redis通过分数从小到大排序

  • zadd set score value

5. hash

      hash用于存储对象

redis与map的区别?

  • map为本地缓存,存在缓存不一致的问题;redis实现分布式缓存,多服务共享同一缓存
  • map只能存放少量的数据,jvm内存过大,容易宕机
  • map存储的是临时数据,服务关闭,缓存即消失,redis可以持久化

持久化

关于redis持久化,可人工输入命令持久化,也可以系统配置。持久化命令有save,bgsave
  • save会造成线程阻塞,因为redis是单线程运行,持久化时后续操作需要等待线程持久化之后继续执行
  • bgsave会创建子线程完成持久化操作,存在的问题是持久化的数据可能不是最新的

持久化存储的形式有两种,分别为
  1. RDB快照,保存系统某一时刻的全部数据,数据为压缩后的二进制文件
  2. AOF,保存所执行的命令语句,客户端输入的操作命令,先缓存在aof缓存中,系统默认配置为一秒钟写入aof文件
RDB与AOF的区别?
  1. 恢复数据时,RDB快照速度快,文件体积小
  2. AOF默认一秒钟持久化一次,相对快照数据丢失率低,数据更加完整(两者同时启用时,redis默认选用AOF恢复数据)
  3. AOF文件体积大,恢复数据慢

过期策略

  1. 定时清理,到某个时间点清理过期的键
  2. 惰性清理,查询数据时,判断数据是否过期,过期则进行删除
  3. 定期清理,每隔一段时间对过期数据进行清理
redis采用了定期清理和惰性清理,所以数据过期,并不一定已经被删除

当定期清理漏掉的过期key过多并长时间未查询,导致redis垃圾数据过多,内存过大,可能影响redis的使用,需要引进内存淘汰策略
内存淘汰策略
  1. 淘汰设置过期时间并访问量最低的数据
  2. 淘汰设置过期时间并即将过期的数据
  3. 淘汰设置过期时间中任意数据
  4. 淘汰访问量最低的数据
  5. 从所有数据中任意淘汰
  6. 禁止淘汰数据 

主从复制

单实例的redis可能存在以下问题:

  • redis挂掉后,系统无法使用
  • redis能承受的访问并发量也是有限的
  • 当大量的访问请求过来时,如果redis无法正常使用,请求将直接到数据库,数据库可能会因此宕机

为了解决以上问题,引入redis的主从复制,读写分离

从节点redis.conf配置以下内容


启动后,主节点状态信息如下:


offset表示复制偏移量,表示的是主节点发送的数据量,从节点接收的数据量

lag表示几秒前有心跳检测

从节点状态信息如下:


主从复制原理:

  1. 设置主服务器IP以及端口,命令为slaveof IP PORT
  2. 与主服务器进行socket连接
  3. 发送ping命令,检验socket状态是否正常,不正常则断开连接重试
  4. 身份校验
  5. 从服务器发送自身IP、端口到主节点记录
  6. 向主节点发送PSYNC命令,执行同步操作,这时主节点有两个操作,第一个是执行bgsave命令,创建子线程生成RDB文件并发送到子节点;第二个是将后续操作命令存放于缓存中并发送到子节点。子节点收到RDB文件恢复数据,此时子节点的数据与主节点生成RDB之前的数据一致
  7. 进入命令传播模式,主节点有写命令操作时,将命令发送给子节点

命令传播模式,如何保证主节点与子节点一直处于连接状态呢?

  • 子节点利用心跳机制定时发送命令给主节点,命令为REPLCONF ACK <replication_offset>,replication_offset表示当前从节点复制偏移量

心跳机制有以下几种作用?

  1. 检查主节点与从节点的网络连接状态
  2. 检查是否有命令丢失,如有主节点将补发命令

同步原理

同步命令:PSYNC runid offset

  1. 全量重同步
  2. 部分重同步
  • offset复制偏移量
  • runid运行ID,redis运行时生成的ID,初次复制时主节点将发送给子节点,同步时,当runid不同时将全量重同步,否则部分重同步
  • 复制缓冲区,为一个队列,先进先出。当进行全量重同步时,一方面生成RDB文件,一方面将写操作将保存到复制缓冲区。同步时当从节点与主节点的offset之差大于缓冲区大小时,将执行全量重同步

主从复制还存在一些问题,当主节点挂掉时,将影响到整个系统。