#五、推理优化、Serving 与部署工程
#代表笔试题
1. Prefill 和 Decode 的瓶颈为什么不同? Prefill 是把用户已有 prompt 一次性喂进模型,计算输入 token 的 hidden states,并生成第一步所需的 KV cache。它的矩阵乘法规模大、并行度高,更容易把 GPU 算力打满,所以偏 compute-bound;长 prompt 会拉高 attention 成本,并决定首 token 前的等待。Decode 是自回归阶段,每一步只新增一个 token,但要读取此前所有 token 的 KV cache。单请求 decode 依赖前一步输出,天然串行;batch 小时 GPU 利用率差,上下文和并发变大时又会被 KV 读写和显存带宽卡住,所以更常见瓶颈是 memory-bound 和调度开销。
2. KV cache 为什么会越来越大? Transformer 在生成第 \(t\) 个 token 时,不能忘掉前 \(t-1\) 个 token 的 key/value,否则每一步都要从头重算整个上下文。KV cache 的大小大致随 batch_size * sequence_length * layer_num * kv_head_num * head_dim * 2 * bytes_per_value 线性增长,其中 2 来自 K 和 V。长上下文、长输出、高并发都会把它放大;GQA/MQA 和 KV 量化只能降低系数,不能改变随活跃 token 增长的事实。它的价值是用显存换速度,代价是显存、碎片、驱逐和调度都变成核心问题。
3. Batching 为什么能提吞吐但不一定降延迟? batching 把多个请求合成一个批次,让矩阵乘法更大、GPU 利用率更高,单位 token 成本下降;但为了凑 batch,请求可能要排队,短请求也可能被长请求拖住,所以单请求延迟尤其是尾延迟可能变差。静态 batching 通常在批次边界等待一组请求一起跑,适合离线或形态相近的请求。continuous batching 则在每个 decode step 动态插入新请求、移除完成请求,让 GPU 持续有活干,更适合在线生成服务。它解决的是“变长请求导致 batch 空洞”的问题,但也要求调度器、KV cache 管理和抢占策略足够成熟。
4. Paged Attention 解决什么? 普通 KV cache 如果要求连续大块显存,变长请求会产生碎片,申请和释放成本也高。paged attention 借鉴虚拟内存,把每个序列的 KV 切成固定大小的 block/page,用页表把逻辑 token 位置映射到物理 KV block。好处是显存利用率更高,可以按页分配、回收、共享和换出;它不是改变模型数学,而是改变 KV cache 的物理组织和 attention kernel 的访存方式。
5. 量化、投机解码、prefix caching 分别优化哪里? 量化把权重、激活或 KV cache 从 FP16/BF16 压到 INT8/INT4/FP8 等格式,主要减少显存和带宽压力,是否加速取决于硬件和 kernel 是否匹配;对 outlier、多模态投影层、长链路推理任务要小心精度损失。speculative decoding 用小 draft model 或轻量分支先猜多个 token,再由大 target model 一次验证;接受率高时可以减少大模型 decode 次数,接受率低或 draft 成本过高时反而不赚。prefix caching 复用相同前缀的 KV,例如系统 prompt、工具说明、RAG 模板或多轮会话公共上下文;它降低重复 prefill 成本,但要求前缀 token 完全一致或有明确的 cache key 设计。
#代表面试题
面试题 1:线上延迟应该怎么拆? 不要只说“平均响应时间”。大模型服务至少要拆成排队时间、prefill 时间、TTFT、decode 阶段的 TPOT、总生成时长和尾延迟。TTFT 是 Time To First Token,用户感知为“是否很快开始输出”;TPOT 是 Time Per Output Token,用户感知为“流式输出是否顺滑”;throughput 可按 requests/s、tokens/s 或 effective tokens/s 统计;latency 要看 p50、p95、p99。SLO 应该写成可执行约束,例如“p95 TTFT 小于 800ms,p95 TPOT 小于 60ms/token,错误率小于 0.1%”。一旦有 SLO,调度器就要做 admission control、队列限长、token 限制和优先级隔离。
面试题 2:首 token 延迟和吞吐怎么折中? TTFT 主要受排队和 prefill 影响,长 prompt 与大 batch 会明显拉高它;吞吐通常受 batch 大小、decode 并发和 GPU 利用率影响。常见折中是给短交互请求更高优先级,用较小 prefill batch 或 chunked prefill 控制首 token;对低优先级批处理任务使用更大 batch;对重复系统 prompt/RAG 模板使用 prefix cache;对长上下文请求设置独立队列,避免挤占短请求。回答时要说明“我不是盲目把 batch 开大”,而是按流量画像把交互、批处理、长上下文、工具调用等请求分池处理。
面试题 3:如何比较 vLLM、TGI、TensorRT-LLM、SGLang 这类推理框架? 不要背功能表,按决策维度比较:模型支持、KV 管理、continuous batching、量化与 kernel、并行策略、speculative decoding、prefix cache、结构化输出、API 兼容性、观测指标和运维复杂度。最终要用目标模型、硬件、prompt 长度分布和 SLO 压测,而不是只看单机 benchmark。
面试题 4:7B、32B、70B 多模型怎么部署? 稳妥设计是拆成路由层、模型服务层和观测/回退层。路由层按任务难度、租户等级、上下文长度、成本预算和实时负载选择模型;简单请求走 7B 或量化模型,复杂推理走 32B/70B,超时或排队过长时降级。模型服务层按模型大小设置并行策略和 KV 配额;观测层追踪 TTFT、TPOT、tokens/s、GPU 利用率、KV 使用率、队列长度、OOM、重试率和质量抽检。
#这一块真正考什么
这部分考察的是你能否把推理看成“计算图 + 显存状态 + 调度队列 + 线上产品约束”的组合系统。不要把优化手段说成并列名词:量化、batching、KV cache、TensorRT、vLLM。系统回答必须先定位瓶颈:是 prefill 算不动、decode 带宽不够、KV 显存爆了、队列太长、租户互相干扰,还是 SLO 定义错了。
部署还必须考虑多租户。多租户不是简单共享一组 GPU,而是要有 per-tenant quota、优先级、最大并发、最大 token、速率限制、成本归因和隔离策略。否则一个长上下文租户就可能占满 KV cache,把短请求的 TTFT 拉爆。成熟服务会设置请求准入、超时、熔断、降级和回退:大模型繁忙时路由到小模型,长输出被截断并提示继续生成,RAG 检索失败时回退到无检索回答或拒答,量化模型质量异常时切回高精度副本。
观测指标也不能只看 GPU utilization。GPU 利用率高可能意味着吞吐好,也可能意味着队列积压。更有用的指标包括:按请求类型分桶的 TTFT/TPOT/p95/p99,prefill 与 decode tokens/s,active sequence 数,KV block 使用率和碎片率,prefix cache hit rate,speculative decoding acceptance rate,量化前后质量抽检,排队时间,取消率,超时率,OOM,重试率和单 token 成本。没有这些指标,优化只能靠猜。
常见误区有七个:把吞吐和延迟混为一谈;只看平均延迟,忽略 p99;认为 KV cache 只会提速,忘记它随上下文和并发膨胀;觉得量化必然无损;认为 speculative decoding 必然加速;把 prefix caching 当成语义缓存,而不是 token 级相同前缀复用;把 batch size 开到最大,以为吞吐最优就是服务最优。
#作答抓手
回答部署题时,用这个框架最稳:流量画像 -> SLO 定义 -> 模型与硬件选型 -> prefill/decode 分析 -> KV cache 管理 -> 调度与 batching -> 量化/投机解码/缓存 -> 多租户隔离 -> 监控、回退与压测。每一步都要说明输入是什么、优化目标是什么、可能牺牲什么。
追问链路可以这样展开: 面试官先问“prefill 和 decode 的区别”,你答出 compute-bound 与 memory-bound;接着追问“为什么显存越来越大”,你用 KV cache 公式解释;再追问“怎么提高吞吐”,你讲 batching、continuous batching 和 paged attention;继续追问“怎么降低延迟”,你拆 TTFT/TPOT、队列和 SLO;再追问“还有哪些优化”,你讲量化、prefix caching、speculative decoding 的适用边界;最后追问“线上怎么兜底”,你讲多租户配额、路由降级、熔断、回滚、质量抽检和观测面板。这样回答的核心优势是:每个术语都挂在一个真实瓶颈上,而不是背工具名。
一句话总结: 大模型 serving 的本质是把有限 GPU 算力和显存,在多租户请求流里,稳定转化为满足 SLO 的 token 输出。prefill 决定首 token 前的计算压力,decode 决定持续输出时的带宽和调度压力,KV cache 决定显存上限,batching 决定吞吐与尾延迟权衡,量化和投机解码决定成本与质量边界,观测和回退决定系统可控。