专栏算法工具链J5 Slice + Squeeze 替换 Gather 算子调试记录

J5 Slice + Squeeze 替换 Gather 算子调试记录

YCJ2025-09-05
52
0

一、背景

在模型开发阶段,我们经常会用到 Gather 算子 来做张量的索引操作
在我的模型中,输入是一个五维张量,形状为:(3, 2, 4, 5, 6)
模型结构里使用了Gather(axis=0),把这个输入在第 0 维上拆成三份,每一份的形状是:(2, 4, 5, 6)
在 PC 上推理没有任何问题,但当模型部署到 J5 开发板上时遇到了算子支持问题

报错信息:


二、问题描述

J5 的算子支持约束下,Gather 算子对输入张量维度有限制。
我这里的输入是五维: (3, 2, 4, 5, 6)
直接使用 Gather 会报错,模型无法正常运行。

换句话说,硬件推理引擎不支持这种用法,必须想办法用受支持的算子来实现相同的逻辑。

三、思路分析

回顾 Gather 的作用:
  • Gather(axis=0, index=i) 等价于 在第 0 维取出第 i 份子张量
  • 输入 (3, 2, 4, 5, 6),取 i=0,1,2,得到三份 (2, 4, 5, 6)。
如果从功能上看,其实就是 在第 0 维上做切片
因此完全可以用 Slice + Squeeze 的组合来替代:
  1. Slice

    • 参数:starts=[i], ends=[i+1], axes=[0], steps=[1]
    • 输出形状:(1, 2, 4, 5, 6)
  2. Squeeze

    • 去掉第 0 维(长度为 1)

    • 得到目标形状 (2, 4, 5, 6)
这样就和原来的 Gather 完全等价。

四、解决方法

通过这个脚本就可以将onnx模型中的所有 Gather 算子Slice + Squeeze 替换

五、效果展示

下面给出 Gather 替换前后的张量切片效果对比

原始 Gather

替换为 Slice+Squeeze

Description
Description
说明:
  • 左图为原始模型使用 Gather(axis=0) 对输入 (3, 2, 4, 5, 6) 的切片输出,每次取第 0 维的一份 (2, 4, 5, 6)。
  • 右图为替换后模型使用 Slice + Squeeze 实现同样的功能,输出形状与原始完全一致。
  • 验证通过 ONNX Runtime 测试,保证替换后模型输出数值等价。

算法工具链
征程5技术深度解析杂谈
评论0
0/1000