柠裳 發表於 2025-10-22 11:21:00

老弟第一次学 Redis,被坑惨了!小白可懂的保姆级 Redis 教程

<p class="md-end-block md-heading"><span class="md-plain">你是小阿巴,刚入职的程序员。</span></p>
<p class="md-end-block md-p"><span class="md-plain">这天,产品经理找到你:阿巴阿巴,用户吐槽咱们网站首页加载太慢,快优化!</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761018848202-d326e77d-fa4d-424b-9d2d-6f2f385d3fb6.png"><img src="https://pic.yupi.icu/1/1761018848202-d326e77d-fa4d-424b-9d2d-6f2f385d3fb6.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你打开监控一看,好家伙!每秒有上万个用户在访问首页,每次都要查询 MySQL 数据库来获取热门文章。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761018914043-d3fa9f00-7e77-4f90-b517-85a317540a19.png"><img src="https://pic.yupi.icu/1/1761018914043-d3fa9f00-7e77-4f90-b517-85a317540a19.png"></span></p>
<p class="md-end-block md-p"><span class="md-plain">虽然你运用毕生所学优化了数据库查询,但它还是扛不住这么高的并发。</span></p>
<p class="md-end-block md-p"><span class="md-plain">你急得满头大汗:数据库快撑不住了,怎么办啊?</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760093779268-3f927ee5-15b9-467b-bbf0-b6c8eb18980c.png"><img src="https://pic.yupi.icu/1/1760093779268-3f927ee5-15b9-467b-bbf0-b6c8eb18980c.png"></span></p>
<p class="md-end-block md-p"><span class="md-plain">这时,你的导师 —— 号称 “后端之狗” 的鱼皮路过,淡定地说了 3 个字:Redis(瑞迪斯)。</span></p>
<p class="md-end-block md-p"><span class="md-plain">你一脸懵:Redis?那是啥?</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761018973225-1b6d7fe9-4923-436a-b8cf-2067d23b24a0.png"><img src="https://pic.yupi.icu/1/1761018973225-1b6d7fe9-4923-436a-b8cf-2067d23b24a0.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">⭐️ 推荐观看本文对应视频:<span class="md-meta-i-c md-link"><span class="md-plain">https://bilibili.com/video/BV1a1sgzfE5d</span></span></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<h3 class="md-end-block md-heading"><span class="md-plain">第一阶段:认识 Redis</span></h3>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:Redis 的全称是 Remote Dictionary Server(远程字典服务器),是一个 <span class="md-pair-s "><strong>基于内存的 K/V 存储系统</strong><span class="md-plain">。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-plain">你:远程?字典?K/V?这些都是什么啊?</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760097443595-5eb8598a-b4ee-42f4-b011-f41da7ac2c9e.jpeg"><img src="https://pic.yupi.icu/1/1760097443595-5eb8598a-b4ee-42f4-b011-f41da7ac2c9e.jpeg"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:你可以把 Redis 当成一个数据库,服务器可以通过网络远程操作它写入和读取数据。K/V 就是 Key-Value 键值对,数据就像字典一样保存。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761019045141-718f2fa5-ee31-4aef-a36a-74c66d2f144f.png"><img src="https://pic.yupi.icu/1/1761019045141-718f2fa5-ee31-4aef-a36a-74c66d2f144f.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你可以通过 Key 快速查询到对应的 Value。而且因为数据存在内存中,Redis 的读写速度有时比 MySQL 快 100 倍!</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761019073038-78221396-0650-46e3-a7d9-b42eeb613d23.png"><img src="https://pic.yupi.icu/1/1761019073038-78221396-0650-46e3-a7d9-b42eeb613d23.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你眼前一亮:那我赶紧装一个试试!</span></p>
<p class="md-end-block md-p"><span class="md-plain">机智如你,直接打开 <span class="md-meta-i-cmd-link"><span class="md-plain">官网</span><span class="md-plain"> 下载了 Redis 服务器,并且成功安装运行。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761019296457-783a57d6-721f-4e3a-986e-12ae23be43ad.png"><img src="https://pic.yupi.icu/1/1761019296457-783a57d6-721f-4e3a-986e-12ae23be43ad.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">但是怎么操作 Redis 呢?</span></p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:可以使用官方提供的命令行工具 Redis CLI 连接并操作 Redis。</span></p>
<p class="md-end-block md-p"><span class="md-plain">打开终端输入下列命令:</span></p>
<pre class="md-fences md-end-block ty-contain-cm modeLoaded"><span>redis-cli&nbsp;<span class="cm-attribute">-h&nbsp;<span class="cm-number">127.0.0.1&nbsp;<span class="cm-attribute">-p&nbsp;<span class="cm-number">6379</span></span></span></span></span></pre>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761019448250-d3da834d-1cd4-4e84-8d55-72bfde36510d.png"><img src="https://pic.yupi.icu/1/1761019448250-d3da834d-1cd4-4e84-8d55-72bfde36510d.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">连上之后,咱们试试最基础的操作,利用 SET 命令保存一个键值对:</span></p>
<pre class="md-fences md-end-block ty-contain-cm modeLoaded"><span>SET name&nbsp;<span class="cm-string">"xiaoaba"</span></span></pre>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">然后通过键读取到值:</span></p>
<pre class="md-fences md-end-block ty-contain-cm modeLoaded"><span>GET name</span></pre>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你刚敲完命令,屏幕立刻返回 "小阿巴"。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761019481716-8bd045d3-42b0-47b5-ad58-4b5fee0e8ff5.png"><img src="https://pic.yupi.icu/1/1761019481716-8bd045d3-42b0-47b5-ad58-4b5fee0e8ff5.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你大为震惊:秒回!这也太快了!</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760098527879-63dbb800-89c6-4938-90dc-918fe49fb34b.jpeg"><img src="https://pic.yupi.icu/1/1760098527879-63dbb800-89c6-4938-90dc-918fe49fb34b.jpeg"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:你刚刚保存的值是 Redis 的 <span class="md-pair-s "><strong>String 字符串</strong><span class="md-plain"> 类型,只是最简单的一种。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-plain">你:还有其他类型?</span></p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:当然,Redis 能存的东西可多着呢~ 它有 5 种基本数据结构,适用于不同场景:</span></p>
<p class="md-end-block md-p"><span class="md-plain">1)String 字符串:存简单的值,比如用户名、计数器</span></p>
<pre class="md-fences md-end-block ty-contain-cm modeLoaded"><span>SET username:1&nbsp;<span class="cm-string">"鱼皮"<br><span>GET username:1</span></span></span></pre>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">2)Hash 哈希表:存对象,比如用户信息 <span class="md-pair-s"><code>{name: "小阿巴", age: 18}</code></span></span></p>
<pre class="md-fences md-end-block ty-contain-cm modeLoaded"><span>HSET user:1001 name&nbsp;<span class="cm-string">"小阿巴"&nbsp;age&nbsp;<span class="cm-number">18<br><span>HGET user:1001 name</span></span></span></span></pre>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">3)List 列表:存有序数据,比如最新的 10 条评论</span></p>
<pre class="md-fences md-end-block ty-contain-cm modeLoaded"><span>LPUSH comments&nbsp;<span class="cm-string">"太棒了!"&nbsp;<span class="cm-string">"学到了"<br><span>LRANGE comments&nbsp;<span class="cm-number">0&nbsp;<span class="cm-attribute">-1</span></span></span></span></span></span></pre>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">4)Set 集合:存不重复的数据,比如点赞用户列表</span></p>
<pre class="md-fences md-end-block ty-contain-cm modeLoaded"><span>SADD post:1:likes user1 user2 user3<br><span>SMEMBERS post:1:likes</span></span></pre>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">5)SortedSet 有序集合:存需要排序且不重复的数据,比如游戏排行榜</span></p>
<pre class="md-fences md-end-block ty-contain-cm modeLoaded"><span>ZADD leaderboard&nbsp;<span class="cm-number">100&nbsp;<span class="cm-string">"玩家A"&nbsp;<span class="cm-number">95&nbsp;<span class="cm-string">"玩家B"&nbsp;<span class="cm-number">90&nbsp;<span class="cm-string">"玩家C"<br><span>ZRANGE leaderboard&nbsp;<span class="cm-number">0&nbsp;<span class="cm-attribute">-1&nbsp;WITHSCORES</span></span></span></span></span></span></span></span></span></span></pre>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024198856-9b8d7a0d-c07f-4c30-87fd-efcb29db7a61.png"><img src="https://pic.yupi.icu/1/1761024198856-9b8d7a0d-c07f-4c30-87fd-efcb29db7a61.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你感叹道:这用法也太多了,我要背这些命令吗?</span></p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:千万别背!用的时候去查 <span class="md-meta-i-cmd-link"><span class="md-plain">Redis 官方的命令手册</span><span class="md-plain"> 就行。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761019868402-8cb81a80-40c7-4ba7-a2f5-be0e1ed79931.png"><img src="https://pic.yupi.icu/1/1761019868402-8cb81a80-40c7-4ba7-a2f5-be0e1ed79931.png"></span></p>
<p class="md-end-block md-p"><span class="md-plain">而且想偷懒的话,推荐你装个 Redis 官方的可视化工具 <span class="md-meta-i-cmd-link"><span class="md-plain">Redis Insight</span><span class="md-plain">,能像操作 Excel 一样操作 Redis,数据一目了然。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024249799-e6107070-0d10-4f5b-b20b-e94e91528567.png"><img src="https://pic.yupi.icu/1/1761024249799-e6107070-0d10-4f5b-b20b-e94e91528567.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你:哇,确实方便多了!但是我怎么用 Java 代码操作 Redis 呢?</span></p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:主流编程语言都有操作 Redis 的客户端 SDK。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760100638556-cae63339-6351-43bd-83b6-3aa527da69f8.png"><img src="https://pic.yupi.icu/1/1760100638556-cae63339-6351-43bd-83b6-3aa527da69f8.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">对于 Java 开发者,可以选择 Jedis、Lettuce、Spring Data Redis 和 Redisson,它们封装了很多操作 Redis 的方法,几行代码就能搞定。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024293530-78eecbb7-669f-4b87-9bd1-efd8cc9083ab.png"><img src="https://pic.yupi.icu/1/1761024293530-78eecbb7-669f-4b87-9bd1-efd8cc9083ab.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">时间充足的话,建议你看看某马的 Redis 教程来系统学习,我当年也看过,讲的很好,先把基础篇和实战篇看完就够了。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024339776-cb55d647-160d-46e9-a366-a01851e59bae.png"><img src="https://pic.yupi.icu/1/1761024339776-cb55d647-160d-46e9-a366-a01851e59bae.png"></span></p>
<p class="md-end-block md-p"><span class="md-plain">你:得咧,我这就看!</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760100890721-bd51ffdf-7720-4b1e-8ea6-fc5b8acbf50d.jpeg"><img src="https://pic.yupi.icu/1/1760100890721-bd51ffdf-7720-4b1e-8ea6-fc5b8acbf50d.jpeg"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<h3 class="md-end-block md-heading"><span class="md-plain">第二阶段:实战应用</span></h3>
<p class="md-end-block md-p"><span class="md-plain">半个月后,你已经看了不少教程,准备解决热门文章查询太慢的问题。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024369973-b8e66649-38c4-49fb-a408-2945edd9f813.png"><img src="https://pic.yupi.icu/1/1761024369973-b8e66649-38c4-49fb-a408-2945edd9f813.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你实现了经典的缓存逻辑:第一次查询时,先从 Redis 中查找,如果没有找到,再从 MySQL 数据库中查询,然后将结果存入 Redis 中,并设置过期时间。后续相同的查询就能直接从 Redis 返回结果。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024382870-9870f966-6fd8-4274-9fbc-4e102d6b45f7.png"><img src="https://pic.yupi.icu/1/1761024382870-9870f966-6fd8-4274-9fbc-4e102d6b45f7.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">示例代码:</span></p>
<pre class="md-fences md-end-block ty-contain-cm modeLoaded"><span><span class="cm-keyword">public&nbsp;<span class="cm-variable">List<span class="cm-operator">&lt;<span class="cm-variable">Article<span class="cm-operator">&gt;&nbsp;<span class="cm-def">getHotArticles() {<br><span>&nbsp; &nbsp;<span class="cm-comment">// 1. 先从 Redis 查询<br><span>&nbsp; &nbsp;<span class="cm-variable-3">String&nbsp;<span class="cm-variable">cacheKey&nbsp;<span class="cm-operator">=&nbsp;<span class="cm-string">"hot_articles";<br><span>&nbsp; &nbsp;<span class="cm-variable-3">String&nbsp;<span class="cm-variable">cachedData&nbsp;<span class="cm-operator">=&nbsp;<span class="cm-variable">redisTemplate.<span class="cm-variable">opsForValue().<span class="cm-variable">get(<span class="cm-variable">cacheKey);<br><span>&nbsp; &nbsp;<span class="cm-keyword">if&nbsp;(<span class="cm-variable">cachedData&nbsp;<span class="cm-operator">!=&nbsp;<span class="cm-atom">null) {<br><span>&nbsp; &nbsp; &nbsp; &nbsp;<span class="cm-comment">// 缓存命中,直接返回<br><span>&nbsp; &nbsp; &nbsp; &nbsp;<span class="cm-keyword">return&nbsp;<span class="cm-variable">JSON.<span class="cm-variable">parseArray(<span class="cm-variable">cachedData,&nbsp;<span class="cm-variable">Article.<span class="cm-keyword">class);<br><span>&nbsp; }<br><span>&nbsp; &nbsp;<span class="cm-comment">// 2. 缓存未命中,查询数据库<br><span>&nbsp; &nbsp;<span class="cm-variable">List<span class="cm-operator">&lt;<span class="cm-variable">Article<span class="cm-operator">&gt;&nbsp;<span class="cm-variable">articles&nbsp;<span class="cm-operator">=&nbsp;<span class="cm-variable">articleMapper.<span class="cm-variable">selectHotArticles();<br><span>&nbsp; &nbsp;<span class="cm-comment">// 3. 将结果存入 Redis,设置 10 分钟过期<br><span>&nbsp; &nbsp;<span class="cm-variable">redisTemplate.<span class="cm-variable">opsForValue().<span class="cm-variable">set(<span class="cm-variable">cacheKey,&nbsp;<span class="cm-variable">JSON.<span class="cm-variable">toJSONString(<span class="cm-variable">articles),&nbsp;<span class="cm-number">10,&nbsp;<span class="cm-variable">TimeUnit.<span class="cm-variable">MINUTES);<br><span>&nbsp; &nbsp;<span class="cm-keyword">return&nbsp;<span class="cm-variable">articles;<br><span>}</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></pre>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">使用 Redis 后,查询速度从 3 秒缩短到了 0.3 秒,产品经理看你的眼神都变了,你很是得意。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024404635-17f90965-4267-486d-91ca-1437ecf7ef03.png"><img src="https://pic.yupi.icu/1/1761024404635-17f90965-4267-486d-91ca-1437ecf7ef03.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:不错,不过 Redis 的作用可不仅仅是缓存,你还能用它继续优化项目么?比如之前用户反馈的登录态失效问题。</span></p>
<p class="md-end-block md-p"><span class="md-plain">你想了想:Redis 的本质是 <span class="md-pair-s "><strong>存储系统</strong><span class="md-plain">,也就是说,可以利用 Redis 来存储多个服务器间需要共享的数据。公司有 2 台服务器,用户第一次登录时,Session 存在服务器 A 本地;刷新页面后,请求被分配到服务器 B,就找不到 Session 了,导致丢失登录态。那我就把需要共享的 Session 数据存到 Redis 中,这样无论请求分配到哪台服务器,都能从 Redis 里拿到 Session。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024433657-db06ec05-6c71-41a5-9231-a8a5b77ae48e.png"><img src="https://pic.yupi.icu/1/1761024433657-db06ec05-6c71-41a5-9231-a8a5b77ae48e.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮欣慰地点了点头:不错,这就是典型的 <span class="md-pair-s "><strong>分布式 Session</strong><span class="md-plain"> 问题。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-plain">类似的,分布式锁也可以利用 Redis 实现,让多个服务器都从 Redis 去获取锁资源,谁先拿到锁,谁就能操作,其他人排队等待。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024446936-a1903f0f-6e50-4258-9997-bdfb7d1289b3.png"><img src="https://pic.yupi.icu/1/1761024446936-a1903f0f-6e50-4258-9997-bdfb7d1289b3.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你:确实,那 Redis 还有其他应用场景么?</span></p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:那可太多了,Redis 除了 5 种基本数据结构外,还提供了很多 <span class="md-pair-s "><strong>“高级” 数据结构</strong><span class="md-plain">,专门解决特定场景的问题。</span></span></span></p>
<ul class="ul-list" data-mark="-">
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-plain">GEO:存地理位置坐标,实现附近的人、附近的餐厅功能</span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-plain">Bitmap:用 1 个 bit 表示一个状态,节约内存,实现用户签到、在线状态统计</span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-plain">HyperLogLog:适用于大规模统计 UV(独立访客数),虽然存在误差,但内存占用只有 12 KB</span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-plain">布隆过滤器:快速判断数据是否存在,可用来防止无效查询打到数据库</span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-plain">Stream:消息队列功能,可以实现异步任务,比如用户下单后异步发送短信通知(但更推荐用专业的消息队列)</span></p>
</li>
</ul>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024464068-86287f1a-9650-4c42-820f-c6e9272cd33c.png"><img src="https://pic.yupi.icu/1/1761024464068-86287f1a-9650-4c42-820f-c6e9272cd33c.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:对了,还有更高级的玩法,Redis 支持编写 <span class="md-pair-s "><strong>Lua 脚本</strong><span class="md-plain"> 保证多个操作的原子性,确保要么全部成功,要么全部失败,避免数据不一致的问题。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024481117-260fd47c-1125-4192-9afd-9ef2505514de.png"><img src="https://pic.yupi.icu/1/1761024481117-260fd47c-1125-4192-9afd-9ef2505514de.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你:这些听起来好高级,感觉学不完了……</span></p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:想什么呢,肯定学不完啊!</span></p>
<p class="md-end-block md-p"><span class="md-plain">Redis 是在持续更新的,去看看 <span class="md-meta-i-cmd-link"><span class="md-plain">官方文档</span><span class="md-plain">,你会发现更多数据结构,比如适用于 AI 应用开发的 <span class="md-meta-i-cmd-link"><span class="md-plain">向量存储</span><span class="md-plain">。不过别担心,可以等实际开发中遇到对应场景再学。</span></span></span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024517028-ee82d3a2-de7e-4b08-b026-8e93618506a0.png"><img src="https://pic.yupi.icu/1/1761024517028-ee82d3a2-de7e-4b08-b026-8e93618506a0.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">Redis 是实战型技术,<span class="md-pair-s "><strong>光看不练等于白学</strong><span class="md-plain">,一定要多动手实践。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-plain">你:好,那我就先给 <span class="md-meta-i-cmd-link"><span class="md-plain">公司网站</span><span class="md-plain"> 的更多查询也加上缓存吧~</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760103690259-12e5464f-034c-4637-b074-4d1ad40f31d3.png"><img src="https://pic.yupi.icu/1/1760103690259-12e5464f-034c-4637-b074-4d1ad40f31d3.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<h3 class="md-end-block md-heading"><span class="md-plain">第三阶段:常见问题和解决方案</span></h3>
<p class="md-end-block md-p"><span class="md-plain">一个月后的某天,凌晨 3 点,你被电话吵醒了。</span></p>
<p class="md-end-block md-p"><span class="md-plain">运维小哥急切地说:阿巴阿巴,网站挂了!数据库查询一直超时,你快看看!</span></p>
<p class="md-end-block md-p"><span class="md-plain">你很是疑惑:都用 Redis 缓存了,还能超时?</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760104000067-a8fb2738-bdac-436b-a370-c4928b85b54a.jpeg"><img src="https://pic.yupi.icu/1/1760104000067-a8fb2738-bdac-436b-a370-c4928b85b54a.jpeg"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你赶紧去公司看了下日志,发现原来有恶意用户在疯狂查询一个不存在的文章 ID,每次 Redis 缓存中都查不到,请求就直接打到了 MySQL 数据库上!</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024561821-79f9dccd-4550-408b-808d-f226ad25c5ae.png"><img src="https://pic.yupi.icu/1/1761024561821-79f9dccd-4550-408b-808d-f226ad25c5ae.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮这时也赶到了公司:这就是经典的 <span class="md-pair-s "><strong>缓存穿透</strong><span class="md-plain"> 问题,恶意请求故意查询不存在的数据,绕过缓存,直接攻击数据库。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024583472-d996dbc0-8466-48ab-aae2-078a97e856fe.png"><img src="https://pic.yupi.icu/1/1761024583472-d996dbc0-8466-48ab-aae2-078a97e856fe.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你汗流浃背了:那怎么办?</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760104492892-7a19761b-23b7-4841-8f5c-c7ea92712bad.png"><img src="https://pic.yupi.icu/1/1760104492892-7a19761b-23b7-4841-8f5c-c7ea92712bad.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:最简单的方法是,即使数据库查询结果为空,仍将这个空结果缓存到 Redis 中,并设置一个较短的过期时间。后续相同请求会直接命中缓存的空值,避免访问数据库。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024618784-d975a62e-c7fc-44f2-982e-d4cd616308ca.png"><img src="https://pic.yupi.icu/1/1761024618784-d975a62e-c7fc-44f2-982e-d4cd616308ca.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你恍然大悟,赶紧写代码补充了缓存空值的逻辑。</span></p>
<pre class="md-fences md-end-block ty-contain-cm modeLoaded"><span><span class="cm-keyword">public&nbsp;<span class="cm-variable">Article&nbsp;<span class="cm-def">getArticleById(<span class="cm-variable-3">Long&nbsp;<span class="cm-variable">id) {<br><span>&nbsp; &nbsp;<span class="cm-variable-3">String&nbsp;<span class="cm-variable">cacheKey&nbsp;<span class="cm-operator">=&nbsp;<span class="cm-string">"article:"&nbsp;<span class="cm-operator">+&nbsp;<span class="cm-variable">id;<br><span>&nbsp; &nbsp;<span class="cm-variable-3">String&nbsp;<span class="cm-variable">cachedData&nbsp;<span class="cm-operator">=&nbsp;<span class="cm-variable">redisTemplate.<span class="cm-variable">opsForValue().<span class="cm-variable">get(<span class="cm-variable">cacheKey);<br><span>&nbsp; &nbsp;<span class="cm-keyword">if&nbsp;(<span class="cm-variable">cachedData&nbsp;<span class="cm-operator">!=&nbsp;<span class="cm-atom">null) {<br><span>&nbsp; &nbsp; &nbsp; &nbsp;<span class="cm-comment">// 如果是空值标识,直接返回 null<br><span>&nbsp; &nbsp; &nbsp; &nbsp;<span class="cm-keyword">if&nbsp;(<span class="cm-string">"__NULL__".<span class="cm-variable">equals(<span class="cm-variable">cachedData)) {<br><span>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span class="cm-keyword">return&nbsp;<span class="cm-atom">null;<br><span>&nbsp; &nbsp; &nbsp; }<br><span>&nbsp; &nbsp; &nbsp; &nbsp;<span class="cm-keyword">return&nbsp;<span class="cm-variable">JSON.<span class="cm-variable">parseObject(<span class="cm-variable">cachedData,&nbsp;<span class="cm-variable">Article.<span class="cm-keyword">class);<br><span>&nbsp; } &nbsp;<br><span>&nbsp; &nbsp;<span class="cm-comment">// 查询数据库<br><span>&nbsp; &nbsp;<span class="cm-variable">Article&nbsp;<span class="cm-variable">article&nbsp;<span class="cm-operator">=&nbsp;<span class="cm-variable">articleMapper.<span class="cm-variable">selectById(<span class="cm-variable">id);<br><span>&nbsp; &nbsp;<span class="cm-keyword">if&nbsp;(<span class="cm-variable">article&nbsp;<span class="cm-operator">!=&nbsp;<span class="cm-atom">null) {<br><span>&nbsp; &nbsp; &nbsp; &nbsp;<span class="cm-comment">// 存储正常数据,10 分钟过期<br><span>&nbsp; &nbsp; &nbsp; &nbsp;<span class="cm-variable">redisTemplate.<span class="cm-variable">opsForValue().<span class="cm-variable">set(<span class="cm-variable">cacheKey,&nbsp;<span class="cm-variable">JSON.<span class="cm-variable">toJSONString(<span class="cm-variable">article),&nbsp;<span class="cm-number">10,&nbsp;<span class="cm-variable">TimeUnit.<span class="cm-variable">MINUTES);<br><span>&nbsp; }&nbsp;<span class="cm-keyword">else&nbsp;{<br><span>&nbsp; &nbsp; &nbsp; &nbsp;<span class="cm-comment">// 存储空值标识,2 分钟过期<br><span>&nbsp; &nbsp; &nbsp; &nbsp;<span class="cm-variable">redisTemplate.<span class="cm-variable">opsForValue().<span class="cm-variable">set(<span class="cm-variable">cacheKey,&nbsp;<span class="cm-string">"NULL",&nbsp;<span class="cm-number">2,&nbsp;<span class="cm-variable">TimeUnit.<span class="cm-variable">MINUTES);<br><span>&nbsp; } &nbsp;<br><span>&nbsp; &nbsp;<span class="cm-keyword">return&nbsp;<span class="cm-variable">article;<br><span>}</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></pre>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮提醒道:缓存穿透只是其中一个问题,实际项目中还会遇到 <span class="md-pair-s "><strong>缓存击穿</strong><span class="md-plain"> 和 <span class="md-pair-s "><strong>缓存雪崩</strong><span class="md-plain">。</span></span></span></span></span></p>
<p class="md-end-block md-p"><span class="md-plain">1)缓存击穿:热门数据突然过期,大量请求同时涌向数据库。可以用互斥锁,让请求排队一个一个来,第一个请求负责查数据库并重建缓存,其他请求等缓存重建完成后再查询。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024643227-0d434554-89b8-4b28-a29d-ccdb629f89dc.png"><img src="https://pic.yupi.icu/1/1761024643227-0d434554-89b8-4b28-a29d-ccdb629f89dc.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">2)缓存雪崩:大量缓存同时过期,数据库瞬间压力巨大。解决方法是给过期时间加上随机值,避免同时失效。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024664305-0b1254ad-e5a6-4dc9-b298-d81d16135a0c.png"><img src="https://pic.yupi.icu/1/1761024664305-0b1254ad-e5a6-4dc9-b298-d81d16135a0c.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你感慨道:Redis 的坑还真不少!</span></p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:这就是为什么要学习 Redis 的最佳实践,比如合理设计缓存键名、设置合适的过期时间、选择正确的数据结构等等。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024702081-bfc75da8-c60c-43b3-89a7-5b59a3c75e08.png"><img src="https://pic.yupi.icu/1/1761024702081-bfc75da8-c60c-43b3-89a7-5b59a3c75e08.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:不过这才刚开始呢,你以后还会遇到缓存和数据库的数据不一致、查询 Redis 阻塞、内存爆满等问题,都是需要学习的,以后我再给你讲吧。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024713244-f0ea7485-2a70-4bc5-afda-d9e3ea4e221c.png"><img src="https://pic.yupi.icu/1/1761024713244-f0ea7485-2a70-4bc5-afda-d9e3ea4e221c.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你:那如果 Redis 本身也扛不住高并发怎么办?</span></p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:那就搭建 <span class="md-pair-s "><strong>多级缓存</strong><span class="md-plain">,比如服务器本地内存缓存 =&gt; Redis 分布式缓存 =&gt; 数据库,层层过滤。用户请求先查本地缓存,没有再查 Redis,还没有才查数据库。每一层都能拦截一部分请求,大大减少 Redis 的压力。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024727571-057721be-c0ee-4ce6-a389-b413c86da941.png"><img src="https://pic.yupi.icu/1/1761024727571-057721be-c0ee-4ce6-a389-b413c86da941.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">还有 <span class="md-pair-s "><strong>缓存预热</strong><span class="md-plain">,比如大促活动前,提前把热门商品数据加载到 Redis 中,避免活动开始时大量请求同时打到数据库。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024741154-d7715c5d-9262-4b3c-9102-eb9784755c80.png"><img src="https://pic.yupi.icu/1/1761024741154-d7715c5d-9262-4b3c-9102-eb9784755c80.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<h3 class="md-end-block md-heading"><span class="md-plain">第四阶段:高级特性和生产部署</span></h3>
<p class="md-end-block md-p"><span class="md-plain">用了一段时间 Redis 后,你开始有点飘了。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760105614961-0cb3a991-1612-42b9-90ce-34cbe9d57ad2.jpeg"><img src="https://pic.yupi.icu/1/1760105614961-0cb3a991-1612-42b9-90ce-34cbe9d57ad2.jpeg"></span></p>
<p class="md-end-block md-p"><span class="md-plain">你对着新来的实习生阿坤炫耀:Redis 我闭着眼睛都能写!什么缓存、分布式锁、多级缓存,我都搞定过!</span></p>
<p class="md-end-block md-p"><span class="md-plain">结果第二天,老板黑着脸找到你:昨晚机房断电重启后,很多用户反馈自己的学习进度丢失了,怎么回事?!</span></p>
<p class="md-end-block md-p"><span class="md-plain">你这才意识到问题的严重性:Redis 数据存储在内存,断电不就没了吗?</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024769156-a305e18e-1b9c-4fac-a0f1-43877e3dda92.png"><img src="https://pic.yupi.icu/1/1761024769156-a305e18e-1b9c-4fac-a0f1-43877e3dda92.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮及时出现:看来你对 Redis 的理解还停留在玩具阶段啊,生产环境的 Redis 可不是这么简单!我来问你几个问题。</span></p>
<p class="md-end-block md-p"><span class="md-pair-s "><strong>第一问:怎么防止数据丢失?</strong></span></p>
<p class="md-end-block md-p"><span class="md-plain">你支支吾吾:做…… 做备份?</span></p>
<p class="md-end-block md-p"><span class="md-plain">没想到,旁边的阿坤突然鸡叫起来:可以利用 Redis 提供的 2 种持久化方案!</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/image-20251021140632837.png"><img src="https://pic.yupi.icu/1/image-20251021140632837.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">1)RDB 快照:定期把内存数据完整保存到硬盘,像拍照一样,恢复快但可能丢失最新数据。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024782537-c1a1a173-bb54-44a6-8931-c3261f5dc9a3.png"><img src="https://pic.yupi.icu/1/1761024782537-c1a1a173-bb54-44a6-8931-c3261f5dc9a3.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">2)AOF 日志:把每个写操作都记录下来,像记日记,数据更安全但恢复较慢(需要重新执行所有写操作)。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024803412-ac1e9e15-287b-44ca-bfc0-36fe3e08dcb5.png"><img src="https://pic.yupi.icu/1/1761024803412-ac1e9e15-287b-44ca-bfc0-36fe3e08dcb5.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-pair-s "><strong>第二问:Redis 服务器挂了怎么办?</strong></span></p>
<p class="md-end-block md-p"><span class="md-plain">你挠头:重启?</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760107095643-da1795b4-f35c-40f9-b9fc-fcc40b73eee2.jpeg"><img src="https://pic.yupi.icu/1/1760107095643-da1795b4-f35c-40f9-b9fc-fcc40b73eee2.jpeg"></span></p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮摇头:用户等得起吗?</span></p>
<p class="md-end-block md-p"><span class="md-plain">阿坤又鸡叫起来:要部署 <span class="md-pair-s "><strong>主从集群</strong><span class="md-plain">,主节点负责写数据,从节点实时同步主节点的数据。这样即使主节点挂了,从节点立刻顶上,用户毫无感知。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024828349-fdd3acaf-ef0d-463c-8d0a-0e3f173673af.png"><img src="https://pic.yupi.icu/1/1761024828349-fdd3acaf-ef0d-463c-8d0a-0e3f173673af.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-pair-s "><strong>第三问:主节点挂了,谁来决定哪个从节点升级?</strong></span></p>
<p class="md-end-block md-p"><span class="md-plain">你无言以对,但是那阿坤竟从容不迫:用 <span class="md-pair-s "><strong>哨兵机制</strong><span class="md-plain">,哨兵就像监工,可以实时监控 Redis 集群健康状态。发现主节点挂了,自动选择一个从节点升级为新主节点,实现自动故障转移。</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024850863-1e6e1a11-d2c1-4f02-af9b-36212044e29f.png"><img src="https://pic.yupi.icu/1/1761024850863-1e6e1a11-d2c1-4f02-af9b-36212044e29f.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-pair-s "><strong>第四问:数据量太大,单台 Redis 存不下怎么办?</strong></span></p>
<p class="md-end-block md-p"><span class="md-plain">你眼前一亮,终于等到自己会的问题了,抢答道:删除数据!</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760107261295-0a79da2d-be85-4030-828b-55347b00b3fb.jpeg"><img src="https://pic.yupi.icu/1/1760107261295-0a79da2d-be85-4030-828b-55347b00b3fb.jpeg"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">阿坤用看流浪狗的眼神看了你一眼,回答道:首先 Redis 自身有多种淘汰策略,会自动删除不常用的数据。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024872013-bc85ce39-6b75-4bf3-b214-f6c37d52dd99.png"><img src="https://pic.yupi.icu/1/1761024872013-bc85ce39-6b75-4bf3-b214-f6c37d52dd99.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">还可以搭建 <span class="md-pair-s "><strong>分片集群</strong><span class="md-plain">,把数据按照某种规则分散到多台 Redis 上,每台只存一部分。Redis 使用 <span class="md-pair-s "><strong>哈希槽</strong><span class="md-plain"> 机制来分配数据,既能存储更多数据,又能承受更高并发。</span></span></span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761024910601-c4b10b9e-51bf-4ee4-815c-c9ee7fba9ef4.png"><img src="https://pic.yupi.icu/1/1761024910601-c4b10b9e-51bf-4ee4-815c-c9ee7fba9ef4.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮拍了拍阿坤的肩膀:小伙子年轻有为啊!</span></p>
<p class="md-end-block md-p"><span class="md-plain">你羞愧地抬不起头:我以为自己已经掌握了 Redis,原来只是学了个皮毛……</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760107531529-5c66503a-ed34-4145-a915-f1f49cd51f6c.jpeg"><img src="https://pic.yupi.icu/1/1760107531529-5c66503a-ed34-4145-a915-f1f49cd51f6c.jpeg"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:这些都是 Redis 在生产环境必须考虑的问题,大厂的 Redis 集群动辄几十上百个节点,就是为了保证 <span class="md-pair-s "><strong>高可用、高性能、高可扩展性</strong><span class="md-plain">。小阿巴,你还要好好跟阿坤学习啊。</span></span></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<h3 class="md-end-block md-heading"><span class="md-plain">第五阶段:深入底层原理</span></h3>
<p class="md-end-block md-p"><span class="md-plain">被鱼皮连环拷问后,你主动找到阿坤:我想深入学习 Redis,不能只停留在会用的层面,请问你是怎么学习底层原理的呀?</span></p>
<p class="md-end-block md-p"><span class="md-plain">阿坤有些惊讶:咦?你不背八股文的么?去 <span class="md-meta-i-cmd-link"><span class="md-plain">面试刷题网站</span><span class="md-plain"> 刷刷题就好了呀!</span></span></span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761025188673-8df0bf1c-3e0b-4352-9479-7fe4f903c870.png"><img src="https://pic.yupi.icu/1/1761025188673-8df0bf1c-3e0b-4352-9479-7fe4f903c870.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你震惊了:现在的校招生,竟然恐怖如斯!</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760107943144-b0551d9a-1cbe-4908-a3d0-b4a20caff7c7.jpeg"><img src="https://pic.yupi.icu/1/1760107943144-b0551d9a-1cbe-4908-a3d0-b4a20caff7c7.jpeg"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:阿坤你别逗他了,其实我们可以带着问题学习。比如你知道 <span class="md-pair-s "><strong>Redis 为什么这么快</strong><span class="md-plain"> 吗?</span></span></span></p>
<p class="md-end-block md-p"><span class="md-plain">你想了想:因为数据存在内存里?</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760107967441-0a8b1fb7-dab5-46ef-9784-3cb897491ffa.jpeg"><img src="https://pic.yupi.icu/1/1760107967441-0a8b1fb7-dab5-46ef-9784-3cb897491ffa.jpeg"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:这只是表面原因。深层次的原因有很多:</span></p>
<ol class="ol-list" start="">
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-plain">高效的数据结构:Redis 底层使用了动态字符串、跳表、压缩列表等经过优化的数据结构</span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-plain">单线程模型:避免了多线程的上下文切换开销</span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-plain">IO 多路复用:一个线程就能同时处理成千上万个连接</span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-plain">内存管理:有完善的内存淘汰策略,比如 LRU 算法</span></p>
</li>
</ol>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761025238540-b992f732-6913-4611-95d0-65fc476dbe69.png"><img src="https://pic.yupi.icu/1/1761025238540-b992f732-6913-4611-95d0-65fc476dbe69.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">你惊讶:单线程还能这么快?</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760108076610-e3dd35d1-1f36-4127-ab46-c736d4b90680.gif"><img src="https://pic.yupi.icu/1/1760108076610-e3dd35d1-1f36-4127-ab46-c736d4b90680.gif"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">鱼皮:对!这就是 Redis 设计的巧妙之处。从这些问题出发,去阅读相关的文章,或者直接像阿坤说的刷一刷 Redis 面试题,就能快速学会很多核心知识点。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761025299571-a2148009-b8cd-49b2-bfe0-595b3ad4e563.png"><img src="https://pic.yupi.icu/1/1761025299571-a2148009-b8cd-49b2-bfe0-595b3ad4e563.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">如果想系统学习,可以看看《Redis 设计与实现》这本书,讲得很透彻;甚至可以看看 Redis 的开源代码。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761025335533-fe9b553f-e495-4621-b720-ff299300e825.png"><img src="https://pic.yupi.icu/1/1761025335533-fe9b553f-e495-4621-b720-ff299300e825.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">要记住,学习底层原理不是为了炫技,而是为了更好地使用 Redis,遇到问题时能够快速定位和解决。</span></p>
<p class="md-end-block md-p"><span class="md-plain">你:好的,我这就去学!</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760100890721-bd51ffdf-7720-4b1e-8ea6-fc5b8acbf50d.jpeg"><img src="https://pic.yupi.icu/1/1760100890721-bd51ffdf-7720-4b1e-8ea6-fc5b8acbf50d.jpeg"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<h3 class="md-end-block md-heading"><span class="md-plain">结尾</span></h3>
<p class="md-end-block md-p"><span class="md-plain">若干年后,你已经成为了公司的 Redis 专家。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1760108814048-f36901f0-462d-49bb-9109-ea6389488f6e.gif"><img src="https://pic.yupi.icu/1/1760108814048-f36901f0-462d-49bb-9109-ea6389488f6e.gif"></span></p>
<p class="md-end-block md-p"><span class="md-plain">不仅能熟练使用 Redis 解决各种业务问题,搭个 Redis 集群架构也是手拿把掐的。</span></p>
<p class="md-end-block md-p"><span class="md-plain">你也像鱼皮当时一样,耐心地给新人分享学习 Redis 的经验,让他们谨记鱼皮的教诲 “Redis 是实战型技术,一定要多动手实践”。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761020681150-54615502-08d8-43c9-931d-aa260c54d57e.png"><img src="https://pic.yupi.icu/1/1761020681150-54615502-08d8-43c9-931d-aa260c54d57e.png"></span></p>
<p class="md-end-block md-p">&nbsp;</p>
<p class="md-end-block md-p"><span class="md-plain">再次遇到鱼皮是在一条昏暗的小巷,此时的他年过 35,灰头土脸。你什么都没说,只是给他点了个赞,投了 2 个币,不打扰,是你的温柔。</span></p>
<p class="md-end-block md-p"><span class="md-image md-img-loaded" data-src="https://pic.yupi.icu/1/1761025361207-4f1e1660-982d-402c-88da-2c17c5593a12.png"><img src="https://pic.yupi.icu/1/1761025361207-4f1e1660-982d-402c-88da-2c17c5593a12.png"></span></p>
<h2 class="md-end-block md-heading"><span class="md-plain">更多编程学习资源</span></h2>
<ul class="ul-list" data-mark="-">
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">Java前端程序员必做项目实战教程+毕设网站</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">程序员免费编程学习交流社区(自学必备)</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">程序员保姆级求职写简历指南(找工作必备)</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">程序员免费面试刷题网站工具(找工作必备)</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新Java零基础入门学习路线 + Java教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新Python零基础入门学习路线 + Python教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新前端零基础入门学习路线 + 前端教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新数据结构和算法零基础入门学习路线 + 算法教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新C++零基础入门学习路线、C++教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新数据库零基础入门学习路线 + 数据库教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新Redis零基础入门学习路线 + Redis教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新计算机基础入门学习路线 + 计算机基础教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新小程序入门学习路线 + 小程序开发教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新SQL零基础入门学习路线 + SQL教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新Linux零基础入门学习路线 + Linux教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新Git/GitHub零基础入门学习路线 + Git教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新操作系统零基础入门学习路线 + 操作系统教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新计算机网络零基础入门学习路线 + 计算机网络教程</span></span></p>
</li>
<li class="md-list-item">
<p class="md-end-block md-p"><span class="md-meta-i-cmd-link"><span class="md-plain">最新设计模式零基础入门学习路线 + 设计模式教程</span></span></p>
</li>
<li class="md-list-item md-focus-container">
<p class="md-end-block md-p md-focus"><span class="md-meta-i-c md-link md-expand"><span class="md-plain">最新软件工程零基础入门学习路线 + 软件工程教程</span></span></p>
</li>
</ul><br><br>
来源:https://www.cnblogs.com/yupi/p/19157536
頁: [1]
查看完整版本: 老弟第一次学 Redis,被坑惨了!小白可懂的保姆级 Redis 教程