- Redis有了解吗?
答:Redis是一款高性能的(Key/Value)分布式数据库,是基于内存运行并支持持久化的NoSQL数据库。因为数据都在内存中,所以运行速度很快。Redis支持丰富的数据类型并且支持事务,事务中的所有命令会被序列化、按顺序执行,在执行的过程中不会被其他客户端发送来的命令打断。
- redis和MemoryCache的那些优势?
-
Memcached所有的值均值简单的字符串,redis作为其替代者,支持更为丰富的数据类型;
-
Redis的速度比memcached快很多,并且Redis支持数据的持久化;
-
redis支持数据的备份,即Master-Slave模式的数据备份。
-
使用底层模型不同,它们之间底层实现方式以及客户端之间通讯的应用协议不一样。Redis构建了VM管理机制;
-
value大小不同,Redis最大可以支持到512MB,而memcached只有1MB。
- Redis都支持哪些数据类型?各自的应用场景?
- 字符串String:Redis中最为基础的数据存储类型,数据结构简单,可以存储文本、Json、图片数据等任何二进制文件。
- 列表List:类似于Java中的List,按照插入顺序排序的字符串链表,在插入时,如果该键并不存在,Redis会为该键创建一个新的链表,与此相反,如果链表中所有元素均被移除,那么该键将会从数据库中清除;可以实现添加一个元素到列表的头部[左边]或者尾部(右边),其底层实现就是一个链表。可以实现一个简单的消息队列功能,做基于Redis的分页功能。
-
集合Set:类似于Java中的Set,但它是一个无序集合。用于存储无序(存入和取出的顺序不一定相同)元素,值不可以重复,可以使用Redis的Set数据类型跟踪一些唯一性的数据,比如访问系统的唯一ip,唯一用户ID。可用于全局去重。
-
有序集合Sorted Set:类似于Java中的Tree Set,支持从小到大排序的Set,可以用于做排行榜应用或者进行范围查找等。
-
Hash:类似于Java中的Hash Map,所以该类非常适合存储值对象信息,比如用户基本信息,对象含有各种用户基本属性(昵称、性别、年龄等)。Key可以作为用户的唯一性ID属性。
除此之外,Redis还支持三种特殊的数据类型,分别是
BitMap(位图)
、Geo(地理坐标)
和HyperLogLog(version 2.8.9中)
。- Redis是单线程的吗?为什么执行速度这么快?
答:redis是单线程的,redis的单线程是指网络请求模块使用了一个线程,所以不需要考虑并发安全性。但是对于需要依赖多个操作的复合操作来说,还是需要锁的,而且有可能是分布式锁。
Redis为什么执行速度如此之快
- 单线程不代表一定就慢,单线程有一个最大的好处就是节省线程切换的开销,更不用考虑并发读写带来的复杂操作场景,这就大大节省了线程间切换的时间了。
- Redis是基于内存的读写操作,内存肯定比传统磁盘IO数据库快。
- Redis核心是基于非阻塞的I/O多路复用技术。
- 单线程操作,避免了多线程的频繁上下文切换,这也避免了多线程可能产生的竞争问题。
多路I/O复用机制
答:Redis线程模型的多路I/O复用机制,目前支持I/O多路复用的系统调用有select、pselect、pol、epoll等函数。I/O多路复用就是通过一种机制一个进程可以监视多个描述符,一旦某个描述符读就绪或者写就绪,其能够通知应用程序进行相应的读写操作。
- Redis的持久化方式有哪些?
答:Redis的持久化方式有两种:RDB和AOF的方式。
-
RDB(快照方式 snapshotting)全量持久化:RDB是Redis默认的持久化方案。在指定的时间间隔内,执行指定次数的写操作,则会将内存中的数据写入到磁盘中,即在指定目录下生成一个dump.rdb文件。Redis重启会通过加载dump.rdb文件恢复数据
-
触发方式:
- 自动触发:在配置文件中,可以配置执行了多少次Save就自动触发自动持久化。
- 手动触发:通过bgsave命令,在后台异步进行生成快照的操作,同时还可以响应客户端的请求。通过redis进行fork操作创建子进程,生成的快照由子进程负责,客户端请求只会在fork阶段被阻塞。
-
优缺点分析:
- RDB持久化方式存在数据丢失,因为其没有办法实现试试持久化。因为bgSave每次运行都要执行fork操作创建子进程,属于重量级操作,频繁执行成本过高,会影响系统性能。自动触发也存在丢失部分数据的情况。
- 再回复大数据集的时候,RDB相对于AOF要快。
-
AOF(append-only-file)(增量持久化):Redis默认不开启,它的出现是为了弥补RDB的不足(RDB可能丢失一个时间窗口的数据),所以它采用日志的形式来记录每一个写操作,生成append only.aof文件,并将日志追加到文件末尾,Redis重启时会根据日志文件的内容将写指令从前到后执行一次已完成数据的恢复操作。
-
AOF日志重写:
- AOF文件会随着服务器运行的时间越来越大,可以通过AOF重写来控制AOF文件的大小。
- AOF重写会首先读取数据库中现有的键值对状态,然后根据类型使用一条命令来替代前面对键值对操作的多条命令。
- 使用命令bgrewriteof来实现AOF重写。
-
AOF重写缓冲区:Redis是单线程工作,当AOF文件较大时重写时间会比较长,在重写AOF期间,redis将长时间无法处理客户端请求。为了解决这个问题,可以将AOF重写程序放到子进程中执行,好处为:
- 子进程进程AOF重写期间,服务器进程(父进程)可以继续处理其他客户端请求。
- 子进程滴啊有父进程的数据副本,使用子进程而不是父进程,可以在避免使用锁的情况下,保证数据的安全性。
-
子进程AOF重写导致的问题:子进程在进程AOF重写期间,服务器进程依然可以处理其他客户端请求,这就会导致数据库状态已经发生了改变,使得当前数据库状态和重写后的AOF文件中的数据不一致。(也就是出现AOF文件和数据库中数据不一致的问题)
-
数据不一致如何解决?
- Redis服务器设置了一个AOF重写缓冲区。这个缓冲区在创建子进程后开始使用,当redis服务器执行一个客户端的写请求命令,之后将这个写命令也发送到AOF重写缓冲区。
- 当子进程完成AOF日志重写之后,给父进程发送信号,父进程接收到此信号后,将AOF重写缓冲区的内容写到新的AOF文件中,保持数据的一致性。
-
优缺点分析:
- AOF文件可以做到秒级持久化,使用追加写的方式来写入,可读性强并且可以使用命令进行文件修复。
- 相比于RDB文件,同样数据下AOF文件体积要大,在Redis负载较高时,秒级更新AOF文件会影响性能。
-
持久化策略选择:
- AOF更安全,可以将数据及时同步到文件中,但是需要更多的磁盘I/O,AOF文件尺寸较大,文件内容恢复相对较慢也更加完整。
- RDB持久化,安全性较差,它是正常时期数据备份及master-slave数据同步的最佳手段,文件尺寸较小且恢复速度较快。