端侧 AI:不只模型更是整机运行合同
传感器、预处理、runtime、CPU/GPU/NPU、内存、热状态、产品门控和更新系统共同决定用户体验。压缩只是在改成本结构;后端分区决定在哪里算;真机证据和整包回滚才决定能否上线。
先说清“边”在哪里,再谈把什么模型放进去
Edge AI(边缘人工智能)泛指让推理或训练靠近数据产生处;On-device AI(设备端 AI)更严格,指任务在终端本机完成;TinyML(Tiny Machine Learning,微型机器学习)通常落在微控制器与 KB~MB 级预算。机房边缘服务器、车载计算盒、手机与传感器 MCU 都叫“边”,运行合同却完全不同。
先算常驻与唤醒
SRAM、Flash 与 duty cycle(占空比)往往比峰值算力重要。唤醒词、振动异常与手势分类通常持续采样,模型即使很小,频繁唤醒也会形成全天功耗。
资源多,但不是独占
CPU、GPU、NPU 与内存还要服务界面、相机和其他 App;后台、低电量、不同 OS 版本和温升会改变调度。一次前台 warm run 不是产品成绩。
数据流与控制周期相连
相机、雷达、麦克风与执行器需要同步。预处理、消息队列和设备 I/O 可能比网络本身更慢,P99 与超时后的安全动作比平均吞吐重要。
失败必须可预测
断网、传感器缺失、backend 编译失败或热降频不能变成无限等待。每个失败路径都要明确:本地降级、拒绝动作、请求人工,或在政策允许时升级云端。
TOPS(Trillions of Operations per Second,每秒万亿次运算)描述特定精度下的理论或峰值运算能力,无法单独回答算子是否受支持、张量是否频繁搬运、模型是否带宽受限、驱动是否稳定,也不包含预处理与产品门控。端侧选型应从完整 workload(工作负载)与 SLO(Service Level Objective,服务等级目标)反推,而不是从芯片营销数字正推。
一次推理走数据面;一个版本靠控制面活下来
数据面负责“这一次输入怎样变成动作”,控制面负责“这个动作在什么设备、什么版本、什么热状态下仍可信”。只交付 checkpoint,会把预处理、runtime、回退、阈值和更新留成不可追溯的隐式状态。
功能链必须端到端测
采样、切帧、resize、tokenize、runtime 初始化、异构执行、去抖、阈值与业务动作都在用户等待时间内。单独测 model.forward() 会漏掉真实瓶颈。
证据必须绑定制品
同一权重换了 tokenizer、driver、后端、量化 scale 或阈值,就不再是同一个产品。manifest(制品清单)要能重建这份完整组合。
先定义失败,再实现成功
权限拒绝、模型损坏、首次编译超时、内存不足、NPU crash、断网与热降频都要有可测试动作;不能把 CPU 回退当作永远安全的默认答案。
一段 20 ms 音频,为什么会变成全天系统账?
- 采样:麦克风与音频前端常驻,系统先支付传感器和 buffer 成本。
- 级联:便宜的 VAD(Voice Activity Detection,语音活动检测)先过滤静音,再让唤醒词模型运行。
- 产品门控:阈值、去抖、连续帧确认决定误唤醒;它们会改变真实调用频率。
- 升级:只有唤醒后才启动更重识别;是否联网、上传哪些字段由政策决定。
P_dynamic ≈ E_inference × r 只是一阶动态功耗:一次推理能耗乘每秒次数。传感器、内存、唤醒、网络与 idle(空闲)仍要另算,因此“单次很省”不等于“全天省电”。
量化、剪枝、蒸馏和协同设计,改的是四笔不同的账
压缩的目标不是得到最小文件,而是在目标设备上,以可接受质量完成更少的计算与搬运。任何方法都要经过“目标后端编译 → 检查分区 → 真机测量”的闭环。
q = clamp(round(r / S) + Z)
r̂ = S × (q − Z)
S 是 scale(尺度),Z 是 zero-point(零点)。Per-tensor、per-channel、per-group 会改变误差与元数据;weight-only 量化只压权重,activation quantization 还改变激活路径。PTQ(Post-Training Quantization,训练后量化)便宜;QAT(Quantization-Aware Training,量化感知训练)在训练中模拟量化,常用于质量敏感场景。仿射表示见 E01。
| 方法 | 直接改变什么 | 什么时候可能真省 | 最常见误判 | 必须补的证据 |
|---|---|---|---|---|
| 量化 | 权重 / 激活 / KV 的位宽与数值表示 | 目标硬件有匹配 kernel,且更少内存流量没有被量化 / 反量化边界吃掉 | “INT4 文件小,所以端到端一定快 8 倍” | 分群质量、kernel 落点、边界转换、文件与峰值内存、冷 / 热分位数 |
| 剪枝 | 零值、通道、block 或 N:M 结构 | 稀疏格式和 sparse kernel 与目标 backend 完全匹配 | 在 dense kernel 上把大量权重置零,就当作减少了计算 | 实际稀疏存储、索引开销、后端支持、端到端 latency 与质量恢复 |
| 蒸馏 | 重新训练学生的层数、宽度、算子与能力分布 | 学生是目标设备友好的稠密架构,且保住长尾与校准 | 只看平均分,忽略教师在难例、拒答和分群上的能力 | 独立 golden set、长尾 / 安全分群、校准、目标机执行与回归 |
| 架构 / 编译协同 | 算子、shape、layout、fusion、buffer 与调度 | 减少不支持算子、跨岛搬运和临时 workspace | 只用 FLOPs 预测真机速度 | 编译报告、partition、tensor timeline、arena、不同设备族的结果 |
N × b / 8 bytes
7B 参数若全部是 4 bit,裸权重下界约 3.5 GB(十进制),即约 3.26 GiB。scale、zero-point、group、对齐、容器、embedding、激活、workspace 与 runtime 都不在里面。
MobileNetV3 把平台延迟写进搜索
论文结合硬件感知 NAS(Neural Architecture Search,神经架构搜索)与 NetAdapt,说明“面向一台真实手机优化”不同于只减理论运算量。它是设计方法证据,不是 2026 手机的固定成绩。E03
MCUNet 把网络和 runtime 一起搜
NeurIPS 正式论文在其 MCU 条件下报告 ImageNet Top-1 超过 70%,TinyEngine 相比所列 TF Lite Micro / CMSIS-NN 基线降低 3.4× 内存并加速 1.7–3.3×。这些数字只属于正式论文设置,不能外推到任意 MCU。E04
NPU 领取的是满足合同的子图,不是整个“模型名”
NPU(Neural Processing Unit,神经网络处理器)后端通常同时检查 operator、dtype、shape、layout、量化参数、OS、driver 与编译器版本。任一条件不满足,图就可能被切开:支持岛交给 NPU,不支持部分留在 CPU / GPU,边界再发生复制、重排、同步或反量化。
op × dtype × shape × layout × quant × OS × driver × compiler × device 因此兼容矩阵必须以“制品 + 软件栈 + 设备族”为单位,而不是只记录 model-v4-int8.bin。
| Runtime | 主要目标 | 官方能力边界 | 上线前实际检查 | 来源 |
|---|---|---|---|---|
| LiteRT CompiledModel | Android / 跨平台移动 | 面向 CPU、GPU、NPU 的编译与自动硬件选择;TensorBuffer 可降低搬运。 | 编译缓存、实际 accelerator、被委托子图、回退、输入输出 buffer 与端到端时间线。 | E13E14 |
| Core ML | Apple 设备 | 框架可使用 CPU、GPU 与 Apple Neural Engine;Core ML Tools 提供量化、palettization 与剪枝。 | 具体 compute unit、算子落点、首次加载、设备 / OS 组合、峰值内存与热态;不能由 API 存在推断整图上 Neural Engine。 | E16E17 |
| ExecuTorch 1.3 文档线 | PyTorch 端侧 | AOT 导出为 .pte,Partitioner 把支持子图交给 delegate,runtime 可做静态内存规划与 selective build。 | export / runtime / backend / SDK 版本、delegate 分区、边界张量、arena、operator 选择与目标机验证。 | E06E07E08E09 |
| ONNX Runtime Mobile | Android / iOS | 先用 CPU / XNNPACK 建基线,再评估 NNAPI / CoreML Execution Provider;可裁剪 operator。 | usability checker 的分区只是预判;必须检查动态 shape、岛数量、EP 切换、二进制大小和真机 P95。 | E18E19E20 |
Android NNAPI 已弃用,不等于今天所有适配器都消失
NNAPI(Neural Networks API)在 Android 8.1 引入,并于 Android 15 被官方标记为 deprecated(弃用)。新的 Android 架构不应把它当长期默认路径;但旧系统、现有 Execution Provider 与厂商栈可能仍存在。迁移决策应分别记录平台政策、runtime adapter 与设备覆盖,不能把“弃用”写成“已删除”。E15
首次安装后可能发生模型校验、AOT artifact 选择、设备编译与 cache 初始化。只报已有 cache 的 warm latency,会把首用卡顿藏起来;同时也不能把某一设备的 cache 初始化时间外推到另一 SoC。至少分别归档下载 / 校验、runtime init、无 cache compile、首次任务与稳定运行。
端侧 LLM 不只装权重,还要养一条不断增长的 KV Cache
生成式模型把端侧问题从“一次前向”变成有状态循环。Prefill(提示词预填充)处理整段上下文,决定 TTFT(Time to First Token,首 Token 等待);Decode(逐 Token 解码)复用 Key-Value Cache,决定 TPS(Tokens per Second,每秒 Token 数)。
B × T × L × 2 × Hkv × Dh × bytes1 × 4096 × 32 × 2 × 8 × 128 × 2 bytes = 536,870,912 bytes = 512 MiB
证据边界:这不是某个具体 checkpoint 的实测峰值,也没有计算 allocator 对齐、滑动窗口、跨层共享、量化元数据、临时张量和 runtime。它只说明上下文翻倍时,标准 KV 账近似翻倍。ExecuTorch 文档也把 KV Cache 与 KV INT8 作为可配置导出项。E10E11
权重与常量
Weight-only INT4 主要压这笔账。裸 4 bit 下界不包含 scale、group、embedding、容器和 runtime;mmap 也不等于零内存。
KV Cache
随 batch、上下文、层数、KV heads 与精度增长。GQA(Grouped-Query Attention,分组查询注意力)通过减少 KV heads 改这笔账。
激活与 workspace
Prefill 的序列长、kernel tiling、attention 实现与并发决定临时峰值;OOM 往往发生在这笔峰值,而不是模型加载时。
产品可主动限预算
限制上下文、截断历史、摘要、滑动窗口、降低并发、分层卸载或云端升级都是系统策略;每种策略都要重新验收质量与隐私。
MLPerf Client 当前 v1.6 页面用提示长度分桶、TTFT 与 TPS 描述客户端 LLM 体验,并设置质量门槛。它比单一“tokens/s”更完整,但仍不能替代你自己的 tokenizer、Prompt 分布、采样参数、持续对话、内存和热稳态测试。E24
冻结测试矩阵,再让六道门共同决定发布
端侧成绩必须绑定设备、软件、状态、温度与输入分桶。平均 latency 会掩盖首用编译、P99 抖动和热降频;单次能耗会掩盖传感器常驻与调用频率;实验室前台成绩会掩盖后台和低电量策略。
常驻唤醒词
- 质量
- 真实噪声分桶的漏唤醒 / 误唤醒
- 延迟
- 从窗口完整到产品动作的 P95 / P99
- 能耗
- J / inference + 全天 duty cycle
- 热态
- 长时间常驻后频率与误报不漂
端侧对话模型
- 质量
- 任务集、长上下文与安全分群
- 交互
- TTFT + 稳态 TPS + 中止响应
- 内存
- 加载、prefill、最大上下文峰值
- 热态
- 10–30 分钟持续生成后的分位数
上面只定义“测什么”,没有给统一门槛。具体毫秒、焦耳、内存和质量阈值必须由业务截止期、目标机型与用户分布决定。
MLPerf Tiny v1.4 同时报告任务质量、延迟与能耗
MLCommons 的 v1.4 轮次覆盖五类 TinyML 工作负载,并支持可选能耗测量。官方结果页列出的 Visual Wake Words 输入为 96×96、质量门槛至少 80%;ColibriNPU 提交报告 22.2 µJ / inference。这个数字证明的是该提交在该 benchmark 协议下的结果,不是任意摄像头、整机待机或产品续航承诺。E21E22
| 维度 | 至少记录 | 可用证据 | 最容易混淆 |
|---|---|---|---|
| 延迟 | 下载 / 校验、init、无 cache compile、cold、warm P50/P95/P99、pre/infer/post | runtime profiler + 系统 trace + 业务时间戳 | 只测 kernel;把 batch throughput 当单用户 latency |
| 内存 | 权重、activation、arena、workspace、KV、峰值与系统杀进程 | Android RSS/PSS/USS、Apple Instruments、runtime allocator | 把文件大小当峰值;跨工具混比 RSS/PSS/USS E27 |
| 能耗 | J / inference、平均功耗、idle、传感器、网络、调用频率 | Android Power Profiler / 外部功率计;Apple Power Profiler | Android ODPM 是设备 / 电源轨口径且有噪声;Apple 工具版本也有限制 E25E28 |
| 热稳态 | 环境温度、机壳、充电状态、thermal status/headroom、时钟与降频后分位数 | 10–30 分钟或业务等长 soak + 平台 thermal API | 拿前 30 秒峰值代表持续运行 E26 |
| 质量 | 总体、设备输入桶、用户分群、校准、FP/FN、回退路径 | 冻结 golden set + 线上脱敏聚合信号 | 压缩后只看平均分;更换预处理却沿用旧基线 |
本地推理减少数据外发,但不会自动获得隐私
“原始数据不出设备”是一条重要控制:它能减少网络与服务端暴露,也能支持离线。但权限、日志、cache、backup、越狱设备、恶意 App、模型提取、更新供应链和遥测重识别仍然存在。风险从云端搬到了终端生命周期,并没有消失。
传感器与权限
是否只在用户可感知场景采集?权限拒绝时能否降级?相机、麦克风、剪贴板与键盘输入是否超过任务最小范围?
中间状态与缓存
原始输入、embedding、activation、KV、个性化状态是否落盘、进入 backup,或被另一个进程读到?密钥和 sandbox 是否覆盖这些路径?
日志与遥测
debug / crash 是否含原文、Prompt、图像路径或特征?采样、聚合、保留期、地域与删除是否可审计?低置信度上传是否真的是最小字段?
模型供应链
制品是否签名?manifest、tokenizer、阈值和动态下载模块能否被替换?坏版本能否离线回滚?旧模型和 cache 删除是否完整?
本地推理
权重固定,输入在设备上变成结果。主问题是权限、存储、日志、联网和终端是否可信。
端上个性化
本地数据改变 adapter、统计量或权重。还要处理漂移、遗忘、撤销、备份和多设备同步。
联邦学习
Federated Averaging 让原始数据留在客户端并聚合模型更新;但更新本身仍可能泄漏。Deep Leakage from Gradients 展示了从梯度重建数据的攻击,因此安全聚合、差分隐私和攻击评测是额外机制。E30E31
每条数据都应回答:为什么需要、在哪里处理、谁能访问、是否写盘、何时上传、保留多久、怎样删除、用户怎样撤回。端侧系统仍属于移动设备安全体系;应用、配置、更新与设备管理要一起看。E32
回滚单位必须是兼容制品,不是孤立的权重文件
模型、runtime、delegate、driver 假设、预后处理、阈值和产品策略共同构成版本。线上质量漂移、OOM、热降频或 backend crash 时,应能按设备族停发,并回到上一份已经通过同一测试矩阵的完整 manifest。
模型 hash、量化 / 稀疏参数、tokenizer / 词表、预处理与后处理版本
设备族、SoC、RAM、OS、driver / SDK、runtime、backend、支持 shape 与已知回退
质量门槛、内存峰值、冷 / 热 P95、能耗、温度、超时、离线与云端升级策略
golden set、分群结果、分区清单、timeline、功耗轨迹、soak test 与失败复现包
制品签名、灰度批次、遥测字段白名单、停发开关、上一份已验证兼容包与回滚演练
只有“质量 × 延迟 × 内存 × 能耗 × 热稳态 × 可靠性 × 隐私”共同通过,版本才算通过
其中任一项失败,选择应是返工模型 / runtime、缩小输入或上下文、改变调用节奏、限定设备族、明确降级,或停止发布。不能用另一项的平均收益抵消一项硬门失败。
01为什么量化后文件小了,P95 却可能更慢?
目标后端可能不支持某些量化算子或 shape,图被切成更多岛;量化 / 反量化、layout 转换、tensor copy 与同步吃掉收益。先看 partition 和 timeline,再谈位宽。
02“有 NPU”为什么不是性能结论?
NPU 只接受满足 operator、dtype、shape、layout、量化、driver 和编译器合同的子图;其余会回退。设备还可能因温度、后台和功耗策略改变调度。
03端侧 LLM 的内存为什么不等于权重大小?
还包括 KV Cache、激活、prefill / decode workspace、runtime、输入输出和 allocator 对齐。长上下文让 KV 近似线性增长,prefill 还可能制造临时峰值。
04怎样证明端侧方案更省电?
在同一设备与固定状态下,测完整任务的 J / inference、调用频率、idle、传感器和网络,再做持续 soak。只测一次 NPU kernel 或瞬时功率不能代表整机全天能耗。
05原始数据不上传,为什么还要做隐私审计?
数据仍可能经权限、日志、cache、backup、恶意 App、模型更新和遥测泄漏。本地推理降低一部分暴露面,不等于匿名、加密、合规或设备可信。
06为什么不能只回滚模型文件?
模型与 tokenizer、预后处理、runtime、delegate、驱动假设、阈值和策略共同通过验证。只换权重可能形成从未测过的组合;应回滚完整签名 manifest。
一手来源与证据边界
优先使用论文、官方文档、官方模型卡和代码仓库。页面中的数字只代表来源所述设置,不自动外推到其他模型与数据。
仿射整数表述、scale、zero-point 与整数推理的原始方法;页面公式据此解释,不把 INT8 当作速度承诺。
剪枝、量化与编码组合压缩的经典研究;论文压缩比只代表当时模型与硬件条件。
把移动端实际延迟带入架构搜索与 NetAdapt 的历史证据,说明 FLOPs 不是唯一优化目标。
TinyNAS 与 TinyEngine 协同设计的原始论文;页面只在其 MCU 与基线设置内复述结果。
知识蒸馏的原始研究,用来区分“重新训练学生”与“直接改同一份权重表示”。
程序准备、runtime 准备、AOT 导出、.pte 制品与静态执行的当前官方架构。
Partitioner 标记连续支持子图并交给 delegate 的官方语义。
固定 arena、张量生命周期、贪心复用与 device-aware buffer 的当前实现说明。
按模型所需算子裁剪 runtime 二进制,而不是把完整算子库一并带上设备。
当前端侧 LLM 导出、KV Cache 开关、KV INT8 与不同后端量化组合的官方入口。
KV Cache 避免每个 decode step 重算整个上下文,以及端侧状态可预测性的官方说明。
QnnPartitioner、受支持子图与 QNN 版本兼容的当前官方边界。
CompiledModel、CPU/GPU/NPU、自动硬件选择、异步与 TensorBuffer / 零拷贝路径的当前官方说明。
Android API 31+、AOT / 设备编译、设备目标化、部分委托与 CPU/GPU 回退的官方说明。
NNAPI 于 Android 15 被弃用及官方迁移方向;“弃用”不写成“已删除”。
在 Apple 设备上调度 CPU、GPU、Neural Engine,以及本地运行与本地更新的官方能力边界。
Palettization、INT4/INT8、剪枝,以及必须按模型、硬件和 compute unit 实测的官方指引。
先以 CPU / XNNPACK 建立基线,再评估 NNAPI / CoreML;分区可能变慢的官方建议。
用分区数量、不支持算子与动态 shape 预判移动后端适配风险;不能替代真机 profile。
按实际模型所需 operator / type 裁剪 ONNX Runtime Mobile 二进制。
TinyML 当前任务、质量门槛、单流延迟与可选能耗测量的官方基准入口。
v1.4 的五类任务、EnergyRunner 与具体提交数据;22.2 µJ 只属于所述 ColibriNPU 提交。
准确率、延迟与能耗共同评价 TinyML 的可复现实验协议。
客户端 LLM 的 Time to First Token、Tokens per Second、提示长度分桶和质量门槛。
ODPM 电源轨数据、支持设备与设备级测量噪声的官方边界。
Thermal status、thermal headroom 与轮询限制;用于长时间压力测试而非单次跑分。
RSS、PSS 与 USS 的定义,避免把不同工具的“内存”数字直接混比。
Xcode Power Profiler 的系统 / App 功耗和 thermal state;页面要求重复采样与固定条件。
Apple 平台真机内存观测与 Instruments 证据入口。
Federated Averaging 原始研究:数据留在客户端、聚合模型更新;不将其等同于自动隐私。
从共享梯度重建训练数据的攻击证据,说明模型更新也可能泄漏信息。
移动设备生命周期、配置、访问、应用与更新安全的系统级威胁背景。