你把一整个代码仓库、工具返回结果和几轮修改记录交给本地 AI,希望它记住前因后果。模型本身也许装得进笔记本,但对话越长,它用来保存上下文的“临时笔记”越厚,内存还是会被挤满。JustFit 想解决的正是这个问题:不只压缩模型,还精打细算地管理推理过程中不断增长的状态。
论文作者 Yuhua Chen 报告,在一台配备 24 GiB 统一内存的 M4 Pro MacBook 上,JustFit 让 Qwen3.8-27B MXFP4 完成了 196,608 个输入 Token和16,384个输出Token,单次请求共占212,992个位置。Token是模型处理文字时切出的基本小块,一个字、词或标点都可能占用一个或多个Token;“位置”则把输入和随后生成的内容都算在内。所以,标题里的“200K-Token”不能理解成20万Token的纯输入窗口。
本文所有系统效果均来自这篇论文及作者自己的实验,没有第二个独立信源复核。它更适合被看作一个完整的系统案例,而不是已经普遍成立的性能结论。
装下模型,只是第一关
本地运行大模型时,最显眼的是模型权重——模型长期保存的参数。Qwen3.8-27B有270亿参数;论文使用固定的MXFP4权重格式。作者估算,即使按理想的四比特存储,权重本身也约需12.6 GiB。
但模型开始读长文后,还会生成KV cache。它可以理解为模型随读随记的草稿:保存已经处理过的上下文中间结果,生成下一个Token时便不必从头计算。上下文越长,这份草稿通常越大。论文称,在这个模型上,192K输入位置对应的FP16 KV状态还要约12 GiB,尚未计入计算工作区和其他状态。两笔账相加,24 GiB笔记本显然没有多少余地。
只把KV cache压小也不够。压缩后的资料在计算前往往需要展开;如果展开多个层所需的临时空间同时留在内存里,仍会在执行途中爆掉。JustFit因此把目标从“文件能否装下”改成“同一时刻究竟有哪些东西必须留在内存”。
它像一间随用随收的工作室
JustFit是一个基于MLX的推理运行时。运行时可以理解为实际调度模型计算、内存和请求的那层软件。它用三个相互配合的机制管理状态,而且这套办法独立于模型权重的量化方式。
第一个机制是KVExec。它把KV状态压成四比特形式,并按256个Token一页保存。模型需要某一层的数据时,KVExec直接按页找到它,在临近计算的位置完成重建。读取、解包和还原尽量合并进行;当前层算完,就限制临时结果继续存活。好比档案平时压缩入库,工作人员只在桌边展开眼前要用的一页,而不是先复印整套档案铺满房间。
按论文给出的模型结构计算,四比特格式在229,376个保留位置上占3,640 MiB;同样的KV若用FP16,则需14,336 MiB。这里约3.94倍的差异只描述KV数据本身,不等于整个程序的内存缩减比例。
第二个机制是PhaseSwap。模型有些组件并非每个阶段都需要,却会长期占着内存。例如用于把内部状态转换成输出词概率的LM head约占644.14 MiB。JustFit在中间的输入处理阶段暂时卸下它,在第一次需要输出结果前再恢复。不过,系统不会机械地每算一步就装卸一次:只要仍有正在生成内容的请求需要该组件,它就继续驻留。决定去留的是“还有谁在使用”,而不只是“眼下执行哪一步”。
第三个机制是StateTrans。它处理请求加入、退出或取消时的交接。系统会等到安全的计算边界,再释放请求占用的页;共享页只有在最后一个使用者离开后才回到空闲池。一个请求结束时,其他请求保留的KV状态和循环状态不必重建。单请求的推测生成与多请求的普通批处理切换时,已有的目标缓存也可以继续使用。
三个机制合起来,做的是同一件事:长期状态尽量压缩,临时数据到用时才展开,组件按实际使用者驻留,请求离场后及时归还资源。
21万位置,具体意味着什么
论文用同一台笔记本和同一模型比较了JustFit与经过测试的mlx-vlm基线。基线完成了24K输入加6K输出,共30,720个位置;到32K输入加6K输出时触及内存保护线。JustFit则在三次独立的新进程测试中,都完成了196,608输入加16,384输出,共212,992个位置。按这一特定口径计算,容量是基线的6.93倍。
这是“完整跑完”的压力测试,不是只把缓存分配出来。测试采用重复文本、贪心选词并抑制提前结束,以控制序列长度;程序仍然实际计算每一个输出Token。三次极限测试的进程峰值为20,960至20,977 MiB,中位生成速度约4.985 tokens/s。
但极限容量并不轻快。论文称,192K冷输入——即没有可复用缓存、需要从头处理——约花48分钟,完整一次测试约103分钟。这更像先花时间整理一套庞大档案,随后在多轮任务中反复利用,而不是每问一句都重新读完20万Token。
前缀缓存因此很重要:如果新请求的大段开头与此前相同,系统可恢复已有状态,只处理新增部分。论文的一项测试恢复了16,383个缓存位置,再处理1个新Token,用时82.314毫秒。不过作者明确指出,这不是20万Token上下文的热启动延迟。
多请求也能共享容量。一次双请求测试保留了合计229,376个位置。这个数字是两个请求的总和,不能当成更大的单请求窗口。它说明压缩后的空间可以被调度给多个请求,而不只是供一个超长任务独占。
容量、速度和内存不是同一张成绩单
论文还报告,32K输入、64输出的短测达到19.11 tokens/s;另一组反复运行的32K输入加6K输出测试,最终配置的进程峰值内存中位数为16,374 MiB,生成速度为11.54 tokens/s。这些数字来自不同负载和不同测试设置,不能拼成“21万位置、19.11 tokens/s、只占16,374 MiB”这样一条不存在的结果。
系统演进中也有取舍。分段KV配置一度达到13.30 tokens/s,快于后来加入分页和生命周期管理的版本;后者却能降低内存并支持多请求共享状态。换句话说,JustFit的重点不是找到一个处处最快的设置,而是在容量、吞吐和请求管理之间做可执行的安排。
作者还用集成运行时测试了30道AIME 2026数学题,四比特分页KV版本答对29道,生成696,834个Token。这个结果至少表明,压缩状态下的系统能够完成长时间生成。但论文没有提供足以排除题目泄漏、采样设置影响等问题的完整对照,因此不能据此断言JustFit提升了模型的推理能力。
为什么值得关注
JustFit最有意思的地方,不是又把某一种数据压小了一点,而是把“哪些状态何时存在”当作核心问题。笔记本的容量有限,真正决定任务能否跑完的,往往不是某个文件有多大,而是权重、KV cache、重建工作区和多请求状态会不会在同一时刻重叠。
这种视角也解释了为什么长上下文不能只看模型标称的窗口长度。能否保存上下文、能否在有限内存中执行注意力计算、请求切换时会不会复制或泄漏状态,都是本地服务的一部分。JustFit把这些环节放在同一个运行时里协调,提供了一个观察内存层级与状态生命周期如何共同工作的完整案例。
局限与未知
- 这是一项单平台、单作者系统研究,核心结果尚无独立复核。极限测试距离21,000 MiB保护线最少只剩23 MiB,日常服务需要更充足的余量。
- 6.93倍来自指定模型、MXFP4权重、mlx-vlm基线和特定测试口径,不能推广成所有本地推理方案都能获得同等提升。
- 容量测试使用重复文本,AIME测试则只覆盖数学题;论文没有证明它能以相同效果完成真实的软件仓库任务,也没有逐项隔离PhaseSwap等机制的贡献。