为什么快?
提到redis,都知道它快。但是为什么快呢?主要是以下几点:
- 纯内存访问,不需要操作磁盘IO,内存的寻址地址为纳秒,可比磁盘快了十万倍;
- 作为NoSQL数据库,数据结构简单,而且是执行命令的核心模块都是单线程,无需做上下文切换;
- 异步处理流程,非阻塞式IO,Redis采用epoll作为多路复用技术的实现;IO模型如图:
IO多路复用技术是以事件驱动的,epoll 在内存中创建一片内存空间,维护两个容器,一个红黑树维护add的fd(文件描述符),另一个维护红黑树里有数据的ready_list。将用户socket对应的fd注册进epoll,然后由epoll监听消息,接发客户消息不会阻塞。
通俗点讲多路复用技术,比如一个班上有一位老师三十个学生,老师收作业,如果按学号一个一个学生的收下去, 如果碰到某个学生出问题,后面的学生都会卡住,效率大打折扣。如果改为学生做完作业了,自己举手示意老师来收作业,效率大大提高。
redis基于epoll等机制抽象出了一套事件驱动型框架,IO多路复用程序监听多个套接字的可读可写事件,将事件交由相应的事件处理器处理。
redis处理过程解析
异步处理IO
redis的核心模块都是单线程工作,还能做到非常快速高效,除了它是完全基于内存操作,还得益于IO处理过程为异步的,是“不连续”的。 假设客户端发送了以下命令
GET key_name
redis回复
test
处理过程可分为四步:
- 接收命令;
- 解析命令;
- 执行命令,将对应的value取出来;
- 返回value。 其中解析和执行操作都为纯cpu/内存操作,接收和返回为IO操作。
用聊天做例子,当你与多人聊天时,当对方显示正在输入时,不等他,去回其他人已发送过来的消息。当你回消息时,消息显示正在发送,也不等待消息发送完毕,又去回其他人消息。而基于事件驱动的可读、可写事件,就像聊天消息提醒一样,告诉你新的消息进来了。
Redis 6.0版本更新了多线程IO,加大了cpu利用率,redis的吞吐量更上一层楼。
redis单机性能实测
环境
- 系统 :CentOS 7.6 64位
- CPU :4 核
- 内存 :8 GB
- 磁盘 :40 GB ESSD 云盘
- Redis :5.0.5
测试工具
redis-benchmark
结果
[root@iZuf6hci646px19gg3hpuwZ ~]# redis-benchmark -t set,get,incr -n 1000000 -q
SET: 85888.52 requests per second
GET: 85881.14 requests per second
INCR: 86722.75 requests per second
常用的 GET/SET/INCR 等命令,都在 8W+ QPS 以上。