turbovec 原理篇(三):Lloyd-Max 量化器如何逼近香农失真-率极限
【免费下载链接】turbovecA vector index built on TurboQuant, written in Rust with Python bindings项目地址: https://gitcode.com/GitHub_Trending/tu/turbovec
turbovec 是一个用 Rust 编写、带 Python 绑定的向量索引库,它的核心是用 Lloyd-Max 标量量化器把每个坐标压到 2~4 bit。这篇文章(原理篇第三篇)回答一个问题:这个量化器的失真到底能逼近理论极限多少?结论先行:实测失真低于香农失真-率下界的 3 倍(官方口径约 2.7 倍),而且整个过程不需要任何训练数据——码本完全由数学推导得出,这是它最反直觉、也最优雅的地方。
为什么需要"压到极限"的量化
先看量化带来的收益:一个 1536 维的 FP32 向量占6,144 字节,压成 2-bit 后只剩384 字节,16 倍压缩。1000 万文档的语料从 31 GB 内存缩进 4 GB,这就是 turbovec 的卖点。
但"压得狠"和"搜得准"是矛盾的——量化失真会直接拖累召回率。所以真正的问题是:
每 bit 能容忍的最小失真到底是多少?我们离它有多远?
信息论给出了答案的地板:香农失真-率极限(Shannon distortion-rate limit)。对均值为 0、方差归一的高斯型坐标,R bit/坐标的量化失真存在一个理论下界:
$$D_{\min} = \frac{2^{-2R}}{d}$$
任何量化器都打不破这个下界;能逼近它的,才算"最优级"量化器。turbovec 的 Lloyd-Max 码本就站在这个地板上不远处。
前提:随机旋转让分布"可预测"
Lloyd-Max 能算出最优码本,前提是知道坐标服从什么分布。turbovec 的聪明之处(见turbovec/src/rotation.rs):
- 归一化:把每个向量拆成"长度 + 单位方向",只量化方向;
- 随机正交旋转:所有向量乘以同一个随机正交矩阵。
旋转之后有一个漂亮的数学事实:单位超球面上的向量,其任意一个坐标都精确服从
$$\mathrm{Beta}\left(\tfrac{d-1}{2},\ \tfrac{d-1}{2}\right) \quad \text{(定义在 } [-1, 1] \text{ 上})$$
且维度 d 足够大时趋近高斯 N(0, 1/d)。关键在于:这个分布与你的数据长什么样完全无关。无论嵌入是 GloVe 还是 OpenAI,旋转后坐标分布都"可预测"——这就是 TurboQuant 论文所说的>比特数
② 卡香农下界:对 d ∈ {256, 768, 1536}、bits ∈ {2, 3, 4} 共 9 个组合断言:
MSE / (2^{-2bits} / d) < 3.0——失真不到下界的 3 倍;MSE / 下界 > 1.0——确实没跌破理论极限(跌破说明算错了)。
README 给出的更精确口径:失真约为香龙失真-率下界的 2.7 倍以内。对"免训练、免调参、在线写入"的量化器来说,这是几乎贴着理论地板在走的水平。
补一刀:消除内积估计的系统性偏差
光"失真接近最优"还不够。标量量化有个隐蔽副作用:重建出来的单位向量比原向量略短,会系统性低估内积分数,低比特时收缩最严重,直接吃掉召回率。
turbovec 的修法(turbovec/src/encode.rs,改编自 RaBitQ):编码时为每个向量算一个标量‖v‖ / ⟨u, x̂⟩(原向量与其重建的内积的倒数补偿),随压缩向量一起存下;检索时打分内核在插入堆之前乘上这个标量——零检索开销、零额外存储,把有偏估计拉回无偏。召回收益在 2-bit 档最明显。
另外可选开启TQ+ 校准(index.calibrate(sample)):用约 1024 行随机样本为每个坐标拟合一个平移和缩放,把有限维度下与 Beta 形状的漂移对齐目标分布。不调用就退化为标准 TurboQuant;调用后在最易漂移的 2-bit 场景上 recall@1 最高 +2.2pp。
自己动手:5 分钟验证"逼近极限"
pip install turbovecfrom turbovec import TurboQuantIndex index = TurboQuantIndex(dim=1536, bit_width=2) # 2-bit 档 index.add(vectors) # float32, shape (n, 1536) scores, indices = index.search(query, k=10)想核对失真数据,直接读仓库源码即可:
- Lloyd-Max 求解器:
turbovec/src/codebook.rs - 编码与长度重归一化:
turbovec/src/encode.rs - 随机旋转与 Beta 分布推导:
turbovec/src/rotation.rs - 失真-率对拍测试:
turbovec/src/kernel_tests.rs - 码本确定性测试:
turbovec/tests/codebook_determinism.rs
小结:一句话记住这一篇
| 关键点 | 结论 |
|---|---|
| 码本从哪来 | 纯数学推导(Beta 分布 + 200 轮 Lloyd-Max 迭代),零训练数据 |
| 失真水平 | 香农失真-率下界的2.7 倍以内 |
| 偏差修正 | 每向量一个标量,内积估计无偏化 |
| 工程代价 | 每形状 25~100 ms,进程级记忆化 |
turbovec 的 Lloyd-Max 量化器 = 已知分布下的"免费最优":分布由随机旋转保证,码本由数学给出,失真贴着香龙地板走——这正是"在线写入、免训练、近最优失真"三者能同时成立的底层原因。
(下一篇预告:bit-pack 布局与 SIMD 查表内核——384 字节的向量是怎么被 NEON/AVX-512 打爆 FAISS 的。)
【免费下载链接】turbovecA vector index built on TurboQuant, written in Rust with Python bindings项目地址: https://gitcode.com/GitHub_Trending/tu/turbovec
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考