如何仅使用所需的运算符来减小 TensorFlow Lite 二进制文件的大小

How to reduce the TensorFlow Lite binary size with only the operators needed

TensorFlow Lite 二进制大小约为 900KB,对我来说仍然很大。我想知道如何仅使用支持模型所需的运算符来减小大小?

Tensorflow 精简版

如果您使用的是 Tensorflow Lite,the only solution I have found is to work at level of Interpreter and customize the Kernel Library (OpResolver). I don't think there is an automatic way of doing this, and the available only example (here the header) 恕我直言,理解起来不是那么容易。我认为在下一个版本中将包含有关此主题的更多改进。此外,我不确定这是否会减少最终库的大小。在 API 注释中,这种方法被认为等同于 选择性注册 ,这在 Tensorflow Mobile 的答案的下一部分中进行了解释。

Tensorflow 移动版

作为问题 "How can I enable only the ops used by my model" 的答案,答案在 Tensorflow Mobile Documentation 中(在二进制大小部分)。

Tensorflow Mobile 的通常大小似乎是 12MB,但可以通过仅包含模型所需的操作来减少它。显然,这需要使用 Bazel 将 Tensorflow Lite 构建为框架。

您可以使用工具 print_selective_registration_header.py 创建一个 header 所需的操作 (ops_to_register.h),该工具可用 here。生成的header应该放在Tensorflow源码目录的根目录下。 您现在已准备好编译库,将 SELECTIVE_REGISTRATION 定义传递给编译器(使用 Bazel 构建,您应该添加选项:--copts=”-DSELECTIVE_REGISTRATION”)。

我认为此过程将使库中的操作最少。其他一些编译器优化标志可能会帮助您调整大小(有时会影响性能)。

编译选项

其实我不知道你是怎么编译代码的(静态库还是动态库),哪些是你在性能方面的需求,哪些是Tensorflow bazelfile中的默认选项,但你可以试试:

  • 将优化减少到 -O1-Os(有时有助于二进制大小,我认为 Tensorflow 的默认框架是 -O2-O3 对于单内核,我不知道精简版。
  • 使用标志 -fdata-section--gc-sections:引用 gcc 文档:“[-fdata-sections] 连同链接器垃圾 collection(链接器 --gc-sections 选项)这些选项可能会导致更小的 statically-linked executables(剥离后)。” (好像linker options for Raspberry Pi中至少用了--gc-sections
  • -fvisibility-inlines-hidden 应该会影响内联函数的性能,但会减小共享 object 的导出 table 的大小。此选项可能 破坏库。一些解释可以看here.
  • 更危险的是-fvisibility=hidden。看看吧here.