<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>底层实现 on 追风笔记</title><link>https://4f0a9a3b.wangpeng.pages.dev/tags/%E5%BA%95%E5%B1%82%E5%AE%9E%E7%8E%B0/</link><description>Recent content in 底层实现 on 追风笔记</description><generator>Hugo</generator><language>zh</language><lastBuildDate>Tue, 25 Aug 2026 00:00:00 +0000</lastBuildDate><atom:link href="https://4f0a9a3b.wangpeng.pages.dev/tags/%E5%BA%95%E5%B1%82%E5%AE%9E%E7%8E%B0/index.xml" rel="self" type="application/rss+xml"/><item><title>Redis 数据结构与底层实现</title><link>https://4f0a9a3b.wangpeng.pages.dev/tech/redis/data-structures/</link><pubDate>Tue, 25 Aug 2026 00:00:00 +0000</pubDate><guid>https://4f0a9a3b.wangpeng.pages.dev/tech/redis/data-structures/</guid><description>&lt;p&gt;Redis 对外暴露五种常用类型，但底层有多种编码（encoding）。根据数据规模自动在不同编码间转换，是它兼顾内存与性能的关键。&lt;/p&gt;&#10;&lt;h2 id="核心底层结构"&gt;核心底层结构&#10;&lt;/h2&gt;&#10;&lt;ul&gt;&#10;&lt;li&gt;&lt;strong&gt;SDS（简单动态字符串）&lt;/strong&gt;：相比 C 字符串记录长度、预分配空间，避免缓冲区溢出并支持二进制安全。&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;ziplist / listpack&lt;/strong&gt;：连续内存的紧凑列表，节省空间，适合小数据量。&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;linkedlist&lt;/strong&gt;：双向链表，元素多时替代 ziplist。&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;dict（字典）&lt;/strong&gt;：哈希表，使用链地址法解决冲突，渐进式 rehash 避免阻塞。&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;skiplist（跳表）&lt;/strong&gt;：多层有序链表，结合 dict 实现 zset，范围查询高效。&lt;/li&gt;&#10;&lt;/ul&gt;&#10;&lt;h2 id="各类型的编码与转换"&gt;各类型的编码与转换&#10;&lt;/h2&gt;&#10;&lt;div class="td-table-scroll td-table-scroll--static"&gt;&#10;&lt;table&gt;&#10; &lt;thead&gt;&#10; &lt;tr&gt;&#10; &lt;th scope="col"&gt;类型&lt;/th&gt;&#10; &lt;th scope="col"&gt;小数据编码&lt;/th&gt;&#10; &lt;th scope="col"&gt;大数据编码&lt;/th&gt;&#10; &lt;th scope="col"&gt;转换阈值（示意）&lt;/th&gt;&#10; &lt;/tr&gt;&#10; &lt;/thead&gt;&#10; &lt;tbody&gt;&#10; &lt;tr&gt;&#10; &lt;td&gt;string&lt;/td&gt;&#10; &lt;td&gt;int / embstr&lt;/td&gt;&#10; &lt;td&gt;raw&lt;/td&gt;&#10; &lt;td&gt;长度 &amp;gt; 44 字节转 raw&lt;/td&gt;&#10; &lt;/tr&gt;&#10; &lt;tr&gt;&#10; &lt;td&gt;hash&lt;/td&gt;&#10; &lt;td&gt;ziplist/listpack&lt;/td&gt;&#10; &lt;td&gt;hashtable&lt;/td&gt;&#10; &lt;td&gt;元素数或单个值超阈值&lt;/td&gt;&#10; &lt;/tr&gt;&#10; &lt;tr&gt;&#10; &lt;td&gt;list&lt;/td&gt;&#10; &lt;td&gt;quicklist（ziplist 片段）&lt;/td&gt;&#10; &lt;td&gt;quicklist&lt;/td&gt;&#10; &lt;td&gt;—&lt;/td&gt;&#10; &lt;/tr&gt;&#10; &lt;tr&gt;&#10; &lt;td&gt;set&lt;/td&gt;&#10; &lt;td&gt;intset&lt;/td&gt;&#10; &lt;td&gt;hashtable&lt;/td&gt;&#10; &lt;td&gt;含非整数或元素过多&lt;/td&gt;&#10; &lt;/tr&gt;&#10; &lt;tr&gt;&#10; &lt;td&gt;zset&lt;/td&gt;&#10; &lt;td&gt;ziplist&lt;/td&gt;&#10; &lt;td&gt;skiplist+dict&lt;/td&gt;&#10; &lt;td&gt;元素数或值长度超阈值&lt;/td&gt;&#10; &lt;/tr&gt;&#10; &lt;/tbody&gt;&#10;&lt;/table&gt;&#10;&lt;/div&gt;&#10;&#10;&lt;p&gt;以 &lt;code&gt;zset&lt;/code&gt; 为例，小数据使用 ziplist 紧凑存储（member 与 score 相邻），当元素数量或单个 member 长度超过阈值时转为 &lt;code&gt;skiplist + dict&lt;/code&gt;，保证有序遍历与按 member 查找都为 O(1)/O(log n)。&lt;/p&gt;&#10;&lt;div class="td-code td-code--untitled" id="td-code-d3cd55a5-fence-0" data-td-code data-td-code-auto-id&#10; data-td-language="text" data-td-line-count="2"&gt;&#10; &lt;div class="td-code__viewport" id="td-code-d3cd55a5-fence-0-viewport" data-td-code-viewport&gt;&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-text" data-lang="text"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;zset 小: [member1, score1, member2, score2, ...] (ziplist)&#10;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;zset 大: dict(member-&amp;gt;score) + skiplist(score-&amp;gt;member)&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;&#10;&lt;/div&gt;&#10;&lt;p&gt;理解这些阈值有助于解释「为什么小哈希比单独 key 省内存」，也提醒我们避免让单个 key 堆积过多元素，否则编码升级或操作耗时都会陡增。&lt;/p&gt;</description></item></channel></rss>