主题
面试速答(先看这里)
**一句话结论:**上面的文章中,介绍过ZipList的级联更新问题。
60秒标准回答:
上面的文章中,介绍过ZipList的级联更新问题。为了解决这个问题,Redis在5.0中推出了一个新的数据结构,那就是我们要介绍的ListPack了
我们知道,ZipList之所以会出现级联更新,主要是因为他的Entry中有个prevlen字段,记录的是上一个Entry的长度,并且在长度不同的情况下可能会用1个或者5个字节表示
那么ListPack为了解决这个问题,其实只要把prevlen干掉就行了,他也正是这么干的, 看下ListPack的结构
**答题顺序:**结论 → 原理/机制 → 关键流程 → 场景与取舍 → 易错点
回答主线:
- **要点1:**我们知道,ZipList之所以会出现级联更新,主要是因为他的Entry中有个prevlen字段,记录的是上一个Entry的长度,并且在长度不同的情况下可能会用1个或者5个字节表示。
- **要点2:**那么ListPack为了解决这个问题,其实只要把prevlen干掉就行了,他也正是这么干的, 看下ListPack的结构:
- **要点3:**主要改动是Entry这里,废弃了原来的prevlen,而是改用了新的方式,用一个backlen来记录整个Entry的字节数。
- **要点4:**就这样,因为ListPack的每个数据项都只会记录自己的长度,而不是再记录上一个节点的长度了,那么,在ListPack中新增或者删除元素,只会影响到这个元素自己,而不需要其他的元素进行级联更新了。
**记忆锚点:**ListPack → Entry → prevlen → ZipList → Redis → 出了一个新的数据结构
加分表达:
- 那么ListPack为了解决这个问题,其实只要把prevlen干掉就行了,他也正是这么干的, 看下ListPack的结构: 主要改动是Entry这里,废弃了原来的prevlen,而是改用了新的方式,用一个backlen来记录整个Entry的字节数。
追问准备:
- 围绕「ListPack」:底层原理是什么?使用时有哪些边界和常见坑?
- 围绕「Entry」:底层原理是什么?使用时有哪些边界和常见坑?
- 围绕「prevlen」:底层原理是什么?使用时有哪些边界和常见坑?
- 如果线上出现异常,你会如何定位、验证并规避?
典型回答
打开文档:✅介绍下Redis中的ZipList和他的级联更新问题
上面的文章中,介绍过ZipList的级联更新问题。为了解决这个问题,Redis在5.0中推出了一个新的数据结构,那就是我们要介绍的ListPack了。
我们知道,ZipList之所以会出现级联更新,主要是因为他的Entry中有个prevlen字段,记录的是上一个Entry的长度,并且在长度不同的情况下可能会用1个或者5个字节表示。
那么ListPack为了解决这个问题,其实只要把prevlen干掉就行了,他也正是这么干的, 看下ListPack的结构:

主要改动是Entry这里,废弃了原来的prevlen,而是改用了新的方式,用一个backlen来记录整个Entry的字节数。并且位于元素末尾。他同样采用变成存储,可以用1-5个字节来存储。
就这样,因为ListPack的每个数据项都只会记录自己的长度,而不是再记录上一个节点的长度了,那么,在ListPack中新增或者删除元素,只会影响到这个元素自己,而不需要其他的元素进行级联更新了。也就解决了级联更新的问题了。