@liweiliwei33
2019-03-01T03:28:44.000000Z
字数 4495
阅读 601
参照官网教程
# 1. 下载 Bazel binary installer named bazel-<version>-installer-linux-x86_64.sh
# 2. Run the installer
chmod +x bazel-<version>-installer-linux-x86_64.sh
./bazel-<version>-installer-linux-x86_64.sh --user
# 3. 设置环境
export PATH="$PATH:$HOME/bin"
git clone https://github.com/tensorflow/tensorflow.git
# 查看版本
git checkout
# 切到你想要的版本
git checkout r1.7
bazel build -c opt //tensorflow/contrib/android:libtensorflow_inference.so \
-- crosstool_top=//external:android/crosstool \
-- host_crosstool_top=@bazel_tools//tools/cpp:toolchain \
-- cpu=armeabi-v7a
这一步就一直报错,怀疑是不是没有装 NDK,然后开始瞎折腾。
安装 NDK
NDK 各版本下载
1. 下载Android NDK自解压包,
官方地址:
https://developer.android.com/ndk/downloads/index.html#download
# 1. 下载:
wget -c http://dl.google.com/android/ndk/android-ndk-r14b-linux-x86_64.bin
# 2. 解压,将Android NDK压缩包解压到你想要的目录下,如 /opt/android/ndk/
chmod a+x android-ndk-r14b-linux-x86_64.bin
./android-ndk-r14b-linux-x86_64.bin
# 解压后目录结构为:/opt/android/ndk/android-ndk-r14b
# 3. 配置PATH路径:
sudo vim /etc/profile
# 在文件末尾加入如下内容:
#set NDK env
export NDK_HOME=/opt/android/ndk/android-ndk-r14b
export PATH=$NDK_HOME:$PATH
# 4. 保存并退出
source /etc/profile
回到 tensorflow 源码目录,编辑 WORKSPACE 文件
#android_ndk_repository(
# name="androidndk",
# path="/opt/android/ndk/android-ndk-r14b",
# # This needs to be 14 or higher to compile TensorFlow.
# # Please specify API level to >= 21 to build for 64-bit
# # archtectures or the Android NDK will automatically select biggest
# # API level that it supports without notice.
# # Note that the NDK version is not the API level.
# api_level=14)
去掉注释,将 path 路径改为 NDK 路径. 编译,仍旧有错,试过r12版本的,也有错,注释掉也是一样的错,可能跟 NDK 没啥关系。
踩了 N 多坑后,将命令行可选项一个个删除,运行,最后,居然出现奇迹了,成功了。
bazel build -c opt //tensorflow/contrib/android:libtensorflow_inference.so
可选项都去掉了,编译了很久。
编译完毕后,libtensorflow_inference.so的路径为:
/tensorflow/bazel-bin/tensorflow/contrib/android
bazel build //tensorflow/contrib/android:android_tensorflow_inference_java
提示没有安装 SDK
安装 SDK
SDK 下载网址
# 1. 解压下载的压缩包
tar -zxvf android-sdk_r24.4.1-linux.tgz
# 2. 安装32位库
sudo apt-get install -y libc6-i386 lib32stdc++6 lib32gcc1 lib32ncurses5 lib32z1
# 3. 配置环境变量
vim /etc/profile
#set android environment
export ANDROID_SDK_HOME=/home/XXX/android/sdk/android-sdk-linux
export PATH=$PATH:${ANDROID_SDK_HOME}/tools
export PATH=$PATH:${ANDROID_SDK_HOME}/platform-tools
# 4. 执行
source /etc/profile
提示没有安装 platform,进入到 android sdk 目录,运行 android,出现 SDK Manager,下载相应的 platform。
回到 tensorflow 源码目录,编辑 WORKSPACE 文件,api_level 与上面下载的 platform 一致。
# Uncomment and update the paths in these entries to build the Android demo.
android_sdk_repository(
name = "androidsdk",
api_level = 26,
# Ensure that you have the build_tools_version below installed in the
# SDK manager as it updates periodically.
build_tools_version = "26.0.1",
# Replace with path to Android SDK on your system
path = "/opt/android/sdk/android-sdk-linux",
)
编译完毕后,android_tensorflow_inference_java.jar的路径为:
/tensorflow/bazel-bin/tensorflow/contrib/android
将 jar 包放在 libs 文件夹下,新建 armeabi 文件夹,加 so 文件放里面,gradle 配置如下
android{
defaultConfig {
# ...
ndk{
abiFilters "armeabi"
}
}
sourceSets{
main{
jniLibs.srcDirs = ['libs']
}
}
}
dependencies {
compile files('libs/libandroid_tensorflow_inference_java.jar')
}
Error:Error converting bytecode to dex:
Cause: Dex cannot parse version 52 byte code.
This is caused by library dependencies that have been compiled using Java 8 or above.
If you are using the 'java' gradle plugin in a library submodule add
targetCompatibility = '1.7'
sourceCompatibility = '1.7'
to that submodule's build.gradle file.
这个问题也是弄了半天,https://stackoverflow.com/questions/37020413/android-dex-cannot-parse-version-52-byte-code 上面的都试了,不行。
我使用的是 Studio 2.2 默认是 Java 7的环境,要支持 java 8,需要在 gradle 文件配置
android{
defaultConfig {
# ...
# 这个很重要,试了很多,就是忘了加这个,一直 bug
jackOptions {
enabled true
}
}
compileOptions{
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
}
jar 包兼容性解决后,又出现下面问题:
java.lang.UnsatisfiedLinkError: dlopen failed: "/data/app/com.aiwac.app.skincare-OQIqPx4ktt9o8ZEG0l3Reg==/lib/arm/libtensorflow_inference.so" is 64-bit instead of 32-bit
可能还是因为编译 so 库时没有加可选项,看了下 so 文件100M 左右,而之前低版本的 so 文件才十几M。
换成java 8后,compile 'org.tensorflow:tensorflow-android:1.7.0' 成功。
网上找到了不同版本的 jar 和 so 文件
https://blog.csdn.net/qq_36440163/article/details/83060160#%C2%A0%204%EF%BC%8CJar%E6%96%87%E4%BB%B6%E5%92%8CSo%E6%96%87%E4%BB%B6%E7%9A%84%E8%A7%A3%E5%86%B3%E6%96%B9%E6%A1%88
替换自己编译的so文件后,终于成功了。
为了在手机/嵌入式设备上使用深度学习模型,我们必须减少模型对内存的占用,减小推理时间和尽量减少耗电。
参照博客 Android TensorFlow 智能语音识别
为了对模型量化权重:
将模型改成protocol buffer文件
从源文件安装,构建tensorflow
在tensorflow目录下执行如下命令
bazel build tensorflow/tools/graph_transforms:transform_graph
bazel-bin/tensorflow/tools/graph_transforms/transform_graph \
--in_graph="/home/liwei/b_graph.pb" \
--out_graph="/home/liwei/mini_graph.pb" \
--outputs="test/prob" \
--transforms="quantize_weights"