第一篇:Redis 为什么这么快?它真的只是因为内存吗? Redis 为什么这么快它真的只是因为内存吗提起 Redis几乎所有人都会说一句话Redis 很快因为数据都放在内存里。这句话没有错但如果只是因为内存快那为什么Java 程序也把数据放在内存里却没有 Redis 快HashMap 同样在内存里为什么不能代替 RedisMemcached 也是内存数据库为什么后来 Redis 成为了主流所以一个真正的问题来了Redis 为什么这么快真的只是因为内存吗今天我们先不分析源码而是先建立整个 Redis 的世界观。很多人都误会了 Redis如果我问 Redis 为什么快估计十个人里面有九个人都会回答因为它是内存数据库。其实这只是第一个原因。如果只有内存这一点那么 Redis 不可能成为高性能缓存的代表。真正让 Redis 快起来的其实是四套设计共同作用。内存 单线程执行模型 IO 多路复用 高效数据结构这四个缺一不可。后面的整个 Redis 系列我们都会围绕它们展开。第一内存访问速度本来就比磁盘快先看一组数量级。大约来说CPU Cache纳秒ns 内存几十到上百纳秒ns SSD几十到几百微秒μs 机械硬盘几毫秒ms注意单位。1ms 1000μs 1μs 1000ns也就是说一次磁盘读取可能已经够 CPU 从内存里读取成千上万次数据。所以MySQL 为什么慢很多时候不是 SQL 慢而是在等待磁盘。而 Redis几乎所有数据都放在内存根本不用等待磁盘这是 Redis 快的基础。但是仅仅这样还远远不够。第二Redis 真的是单线程吗很多人第一次学 Redis。老师都会说Redis 是单线程。于是很多人开始疑惑。单线程不是应该更慢吗为什么 Redis 反而这么快事实上这里隐藏着一个最大的误区。Redis 并不是整个程序只有一个线程。真正单线程的是命令执行、网络收发、后台持久化、AOF Rewrite、主从同步这些都有自己的线程真正串行执行的只是SET GET HSET ZADD这些命令为什么这样设计因为没有锁。没有线程竞争、没有上下文切换、也没有大量同步开销。于是命令执行反而更快。下一篇我们就专门分析Redis 为什么宁愿单线程也不用多线程处理命令第三Redis 快不只是因为内存还有 IO假设10000 个客户端同时连接 Redis是不是就需要10000 个线程很多人都会这样想事实上Redis 根本不会这么做。它采用的是IO 多路复用。简单来说就是一个线程同时监听很多连接谁有数据先处理谁不用为每一个连接创建一个线程。这样CPU 利用率更高、线程数量更少、上下文切换更少整个网络模型也更高效。所以很多人口中的Redis 单线程。实际上包含了事件驱动 IO 多路复用。这也是 Redis 高性能的重要原因之一。第四Redis 的数据结构设计非常变态很多人觉得 Redis 就五种数据类型。String List Hash Set ZSet其实这只是我们看到的数据类型。真正底层Redis 为它们设计了很多专门的数据结构。例如String不是 Java String而是SDSSimple Dynamic StringList不是普通链表而是QuickListZSet也不是 TreeMap而是SkipList跳表Hash也会根据数据规模自动切换不同编码。也就是说。Redis 并不是只有五种数据结构。而是根据不同业务场景自动选择最合适的底层实现。后面的文章我们都会一个一个揭秘。所以Redis 到底为什么快如果现在再回答这个问题真正完整的答案应该是第一数据放在内存避免了磁盘 IO。第二命令采用串行执行没有锁竞争。第三采用 IO 多路复用一个线程管理大量连接。第四针对不同业务设计了大量高性能数据结构。很多文章只讲了第一点实际上后面三点才是真正体现 Redis 设计能力的地方。Redis 真正厉害的地方不是快很多公司把 Redis 当缓存。于是很多人觉得Redis 的价值就是快。其实不是。Redis 真正厉害的是为了做到快它几乎把整个系统都重新设计了一遍。为什么不用 Java String为什么不用 LinkedList为什么不用红黑树为什么不用多线程为什么不用每次都写磁盘这些设计最终共同造就了今天的 Redis。而这也是整个 Redis 源码最值得学习的地方。总结很多人觉得Redis 快就是因为内存实际上内存只是基础。真正让 Redis 成为高性能缓存的是四个核心设计内存访问单线程命令执行模型IO 多路复用高效的数据结构**后面的整个 Redis 系列我们就围绕这四个问题一步一步拆开 Redis 的底层设计。相信你会发现Redis 的精彩从来都不只是一个缓存。上一篇《SqlSession 为什么不是线程安全的》下一篇《Redis 为什么选择单线程性能为什么还能这么高》如果这篇文章让你第一次发现Redis 快并不只是因为内存欢迎点个赞。你也可以在评论区聊聊在你看来Redis 最让你意外的设计是什么是单线程、跳表还是 SDS