推理优化 · 性能指标与诊断
先能区分 TTFT、TPOT、吞吐和 P95。测法和 KPI 定义看全量笔记。
0. 总图
线上别只报「tokens/s」。延迟、吞吐、推测解码要分开看,否则会用吞吐掩盖尾延迟。
延迟
| 指标 | 含义 | 主要卡在哪 |
|---|---|---|
| TTFT | 发请求到第一个 token | Prefill,prompt 越长越慢 |
| TPOT | 相邻输出 token 的间隔 | Decode,受 batch 影响 |
| TTFB | 首字节网络返回 | 排队 + 网关 + Prefill |
聊天体感:TTFT 决定「是不是卡住了」,TPOT 决定「字是不是一个一个往外蹦」。Batch 开大,吞吐上去,TPOT 往往变差。
吞吐
- Throughput — 总生成 token / 总时间。看卡填得满不满。
- Goodput — 满足延迟约束的请求数/秒(例如 TTFT < 1s 且 TPOT < 100ms)。吞吐很高但全超时,Goodput 接近 0。
- GPU 利用率 — 看 Compute Utilization,不是显存占用。显存 90%、算力 20% 就是 Decode Memory-Bound。
必须 stream=True 打时间戳。非流式只能拿到整段结束时间,分不开首字和后续间隔。测之前先预热,丢掉 CUDA JIT / 显存分配的冷启动。
先查什么
TTFT 过高(体感常约 2 秒)
- prompt 很长且并发不低 → Prefill Compute-Bound。整段 Prefill 独占 GPU,别人的 Decode 在等。
- KV 占用已经很高(经验超过约 0.9)→ Memory-Bound / Swapping。首 token 被换页拖死。
- 短 Prompt 反而最慢 → 先怀疑冷启动,不要据此调参。
TPOT 毛刺 / 卡顿
- 同一张卡上突然来一条长 Prefill → 先 Chunked Prefill,再考虑 PD 分离。
- batch 过大 → 吞吐换来了间隔变差。
吞吐不涨
- 并发扫上去,吞吐几乎不涨或延迟同比翻 → Continuous Batching 没生效,或 KV/调度已经卡住。
- 还在 Memory-Bound 时:并发涨、吞吐涨、P50 几乎不动,才像持续批在工作。
何时调哪一层
| 现象 | 先动 | 先别动 |
|---|---|---|
| TTFT 高、prompt 长 | Chunked Prefill、Prefix Caching | 只加大 batch |
| KV 在 swap | 减并发、量化 KV、加卡 | 只切 Prefill 块 |
| 吞吐低、P50 稳 | 开大并发到拐点前 | 把 max-num-seqs 开过拐点 |
| Decode 慢、batch 小 | 推测解码 | 大 batch 上硬开草稿 |
| Prefill 与 Decode 互抢且流量大 | PD 分离 | 小流量短请求上拆池 |
vLLM 上和这组指标绑在一起的旋钮:max-model-len × max-num-seqs 决定 KV 下限;gpu-memory-utilization 是总盘子;enable-chunked-prefill、enable-prefix-caching 是 TTFT 常用开关。PagedAttention 只管怎么切块,盘子不够照样 OOM。
所有性能数字都以当前模型、版本、硬件、上下文和并发压测为准。
深入
- 关键性能指标
- TTFT 诊断、并发如何验证持续批:见 推理优化 · 技术问答