2、稀疏化基础:稀疏化定义、类型(结构化/非结构化)、稀疏度指标与模型压缩收益

TinyML 模型部署的最大瓶颈,从来不是“精度不够”,而是“资源装不下”。一个 300KB 的模型在 PC 上运行毫无压力,但放到仅有 256KB Flash 和 64KB RAM 的 MCU 上,连加载都成问题。稀疏化(Sparsity)正是解决这一矛盾的核心手段之一:通过将模型中大量接近零的权重直接置零并跳过计算,从而同时压缩存储体积和减少推理计算量。本章将系统梳理稀疏化的数学定义、两种主流类型(结构化与非结构化)、衡量稀疏程度的指标体系,以及稀疏化带来的真实压缩收益与代价。

稀疏化知识框架:定义 → 类型 → 指标 → 收益 稀疏化 Sparsity 定义 权重张量中零值占比 数学:||W||₀ / total 目的:跳过无效计算 类型 非结构化:任意位置置零 结构化:整行/整列/通道置零 硬件友好度差异显著 稀疏度指标 全局稀疏度 / 层间稀疏度 权重稀疏度 / 激活稀疏度 粒度:细粒度/粗粒度 压缩收益 存储:Flash 占用下降 计算:MACs 减少 能耗:电池续航提升 图:稀疏化核心知识体系 — 四要素相互关联,决定 TinyML 部署效果

2.1 稀疏化的数学定义与本质

稀疏化本质上是对神经网络权重张量(Weight Tensor)或激活张量(Activation Tensor)中冗余信息的一种“剪除”操作。从线性代数角度看,一个权重矩阵 W 的稀疏度定义为:

Sparsity = (||W||₀) / (m × n)

其中 ||W||₀ 表示矩阵中非零元素的个数(L0 范数),m × n 为矩阵总元素数。稀疏度越高,意味着越多的权重被置为零。例如一个 4×4 的卷积核矩阵,若其中 12 个元素为 0,则稀疏度为 75%。

但稀疏化并非简单的“随机丢权重”。其核心依据是:神经网络在训练收敛后,大量权重值趋近于零,这些权重对最终输出的贡献微乎其微。通过将这些权重置零,我们可以在几乎不影响模型精度的前提下,获得存储和计算上的双重收益。在 TinyML 场景中,这种收益直接转化为:Flash 占用减少、RAM 峰值降低、推理延迟缩短、电池续航延长。

关键认知:稀疏化不是“破坏模型”,而是“识别并移除冗余”。一个训练良好的模型,其有效信息往往集中在少数关键连接上,这被称为“彩票假设”(Lottery Ticket Hypothesis)。稀疏化正是利用了这一特性。

2.2 稀疏化类型:非结构化 vs 结构化

根据置零权重的分布模式,稀疏化分为两大类,它们在硬件友好性、压缩效率和实现难度上差异巨大。

对比维度 非结构化稀疏(Fine-grained) 结构化稀疏(Coarse-grained)
置零粒度 单个权重元素 整行、整列、整个通道或滤波器
稀疏度上限 可达 90%~95% 通常 50%~75%
硬件加速 需要专用稀疏计算单元(如 EIE、Sparse CNN 加速器) 通用 CPU/DSP 可直接受益,无需特殊硬件
存储压缩 需索引编码(如 CSR/CSC),额外开销 可直接删除整块数据,压缩简单
精度损失 同等稀疏度下精度损失更小 同等稀疏度下精度损失更大
典型应用 云端大模型压缩 TinyML 边缘设备部署

非结构化稀疏的典型代表是权重剪枝(Weight Pruning)。训练完成后,将绝对值小于阈值的权重直接置零。这种方式的优点是稀疏度高、精度损失小,但缺点是权重在内存中的分布变得“支离破碎”,CPU 无法连续读取有效数据,必须依赖索引表(如 CSR 格式)来定位非零元素,这反而增加了额外的存储和计算开销。在 Cortex-M 级别的 MCU 上,非结构化稀疏往往得不偿失。

结构化稀疏则完全不同。它按规则模式置零,例如将某个 3×3 卷积核的整行置零,或者将整个输出通道剪掉。这样处理后,权重矩阵仍然保持规则的矩形结构,CPU 可以连续读取数据,无需索引表。虽然稀疏度上限较低,但在实际 TinyML 部署中,结构化稀疏带来的“有效加速比”往往更高。

常见误区:很多初学者认为“稀疏度越高越好”。实际上,在 MCU 上,非结构化稀疏度达到 80% 时,由于索引开销,实际推理速度可能比稠密模型还慢。选择稀疏化类型时,必须结合目标硬件的计算特性。

2.3 稀疏度指标体系:如何量化与评估

稀疏化训练过程中,我们需要一套完整的指标来监控稀疏化效果和模型健康度。仅看“全局稀疏度”远远不够,必须分层、分维度地观察。

2.3.1 核心指标定义

  • 全局稀疏度(Global Sparsity):整个模型中零值权重占总权重数的比例。公式:S_global = (总零值数) / (总权重数)。用于宏观评估压缩潜力。
  • 层间稀疏度(Layer-wise Sparsity):每一层独立的稀疏度。不同层对稀疏化的敏感度差异极大,全连接层通常比卷积层更“耐剪”。
  • 权重稀疏度 vs 激活稀疏度:权重稀疏度指静态参数中的零值比例;激活稀疏度指推理过程中特征图(Feature Map)中零值的动态比例。激活稀疏度往往更高(ReLU 后可达 50%+),但利用难度更大。
  • 粒度(Granularity):描述稀疏模式的最小单元。细粒度(1×1 元素)、中等粒度(1×4 块)、粗粒度(整个通道)。粒度越粗,硬件加速越容易,但精度损失越大。

2.3.2 判断稀疏化质量的综合指标

仅看稀疏度数字是不够的,必须结合以下指标综合判断:

  1. 精度保留率:稀疏化后模型在验证集上的 Top-1/Top-5 精度与原始模型的比值。通常要求 ≥98%。
  2. 有效计算减少率:实际跳过的 MACs(乘加运算)比例。对于结构化稀疏,这个值约等于稀疏度;对于非结构化稀疏,需要根据硬件支持情况计算。
  3. 模型体积压缩比:稀疏化后模型文件大小与原始大小的比值。注意,非结构化稀疏需要额外存储索引,压缩比会打折扣。
  4. 推理延迟变化:在目标 MCU 上实测的推理时间变化。这是最终衡量标准。
实操建议:在训练日志中同时记录“全局稀疏度”和“每层稀疏度分布”。如果发现某一层稀疏度远低于其他层,说明该层是“稀疏瓶颈”,需要调整该层的剪枝阈值或正则化强度。

2.4 模型压缩收益:从理论到实际部署

稀疏化的收益不能只看“参数少了多少”,必须从存储、计算、能耗三个维度综合评估。

2.4.1 存储收益(Flash 占用)

对于结构化稀疏,假设原始模型为 300KB,稀疏度为 60%,则理论上 Flash 占用可降至 120KB。但实际中,还需要考虑存储格式的开销。对于非结构化稀疏,使用 CSR 格式存储时,每个非零元素需要额外存储列索引(通常 2 字节),当稀疏度低于 70% 时,压缩收益会被索引开销大幅抵消。

// 示例:CSR 格式存储稀疏矩阵
// 原始 4×4 矩阵,稀疏度 75%(12 个零,4 个非零)
// 存储内容:
// values:    [1.2, 3.4, 5.6, 7.8]      // 4 个非零值
// col_idx:   [0, 2, 1, 3]              // 每个非零值的列号
// row_ptr:   [0, 1, 2, 4]              // 每行起始位置
// 总存储:4×4B + 4×2B + 4×2B = 32B
// 原始稠密存储:16×4B = 64B
// 压缩比:2:1(但稀疏度需 ≥75% 才有此效果)

2.4.2 计算收益(MACs 减少)

在 MCU 上,乘加运算(MAC)是最耗时的操作。稀疏化后,跳过的 MACs 数量直接决定推理加速比。对于结构化稀疏(如通道剪枝),加速比 ≈ 1/(1-稀疏度)。例如稀疏度 50% 时,理论加速 2 倍;稀疏度 75% 时,理论加速 4 倍。但实际中,由于内存访问瓶颈,加速比通常达不到理论值。

2.4.3 能耗收益

对于电池供电的 TinyML 设备,能耗是关键指标。跳过计算意味着减少 CPU 活动时间,从而降低动态功耗。根据实验数据,在 ARM Cortex-M4 上,稀疏度 50% 的结构化稀疏模型,推理能耗可降低约 40%。

2.5 案例拆解:8KB 模型在 Cortex-M0+ 上的稀疏化实战

下面通过一个完整的案例,展示稀疏化从设计到部署的全过程。

背景与约束:某智能传感器项目需要部署一个关键词唤醒(KWS)模型,目标硬件为 STM32L0 系列(Cortex-M0+,32MHz,Flash 64KB,RAM 8KB)。原始模型为 2 层卷积 + 2 层全连接,参数量 45,000,模型大小 180KB,远超 Flash 限制。

初始目标:将模型压缩至 32KB 以内,同时保证唤醒准确率 ≥95%(原始准确率 97.2%)。

关键参数与指标:

层名称 参数量 原始稀疏度 目标稀疏度 敏感度
Conv1 (3×3×16) 448 5% 30% 高
Conv2 (3×3×32) 9,248 8% 50% 中
FC1 (512×128) 65,664 12% 80% 低
FC2 (128×10) 1,290 10% 60% 中

分析判断过程:首先,通过逐层剪枝敏感性分析(每层单独剪枝 10%,观察精度变化),发现 FC1 层对剪枝最不敏感,而 Conv1 层最敏感。因此,决定采用“差异化稀疏度策略”:FC 层使用高稀疏度(70%~80%),Conv 层使用低稀疏度(30%~50%)。同时,考虑到 Cortex-M0+ 不支持稀疏计算指令,决定采用结构化通道剪枝而非细粒度剪枝。

实际操作步骤:

  1. 使用 TensorFlow 训练原始模型,达到 97.2% 准确率。
  2. 对 FC1 层执行通道剪枝(每个神经元对应一个输出通道),逐步将 512 个神经元剪至 128 个。
  3. 对 Conv2 层执行滤波器剪枝,将 32 个滤波器剪至 16 个。
  4. 剪枝后微调(Fine-tune)5 个 epoch,学习率设为原训练时的 1/10。
  5. 量化至 int8 后,模型大小降至 28KB。

结果对比:

指标 原始模型 稀疏化+量化后 变化
模型大小 180KB 28KB ↓84%
准确率 97.2% 95.8% ↓1.4%
推理时间 无法运行 38ms 满足实时性
RAM 占用 无法运行 6.2KB 满足 8KB 限制

风险与代价:结构化剪枝导致 Conv1 层信息丢失较多,准确率下降超出预期。通过将 Conv1 的剪枝率从 30% 降至 20%,并增加一个 epoch 的微调,最终准确率回升至 96.1%。代价是模型大小增加 2KB。

复盘经验:在 TinyML 场景中,结构化稀疏 + 量化的组合远比单一非结构化稀疏有效。稀疏化训练必须与目标硬件协同设计,不能脱离硬件谈稀疏度。此外,逐层敏感度分析是稀疏化训练 schedule 设计的第一步,它决定了各层稀疏度的分配策略。

重要提醒:稀疏化不是“训练后处理”的附加步骤,而应作为训练过程的一部分。在训练中动态调整稀疏度(渐进式剪枝)比训练后一次性剪枝效果更好,这将在后续章节详细展开。

2.6 常见误区与总结

稀疏化基础阶段,以下误区需要特别警惕:

  • 误区一:稀疏度越高越好。实际上,超过一定阈值后,精度会急剧下降,且硬件加速收益趋于饱和。建议在 TinyML 中,非结构化稀疏度不超过 85%,结构化稀疏度不超过 70%。
  • 误区二:忽略索引开销。非结构化稀疏在存储时,索引表可能占据 30%~50% 的额外空间。计算“有效压缩比”时,必须将索引计入。
  • 误区三:只看权重稀疏度,不看激活稀疏度。在 TinyML 中,激活稀疏度对计算加速同样重要,尤其是在使用 ReLU 的模型中。
  • 误区四:所有层使用相同的稀疏度。不同层对稀疏化的敏感度差异巨大,必须差异化设计。

总结而言,稀疏化是 TinyML 模型压缩的基石。理解其定义、类型、指标和收益,是后续设计稀疏化训练 schedule 的前提。下一阶段,我们将深入探讨如何在训练过程中动态控制稀疏度,以及如何设计合理的 schedule 策略。