本文内容来自ling9601MNN GitHubissues_1051的回答,加上笔者实测过程中的一些注释。

由于MNN没有用于树莓派4B的pip安装包,所以需要在树莓派上使用python版的MNN的话可以自己编译whl文件,然后安装。

或者直接尝试安装笔者编译的whl包:点这里,安装失败再自行编译。

笔者使用的树莓派4B系统为2021-05-07-raspios-buster-armhf ,内存4GB。

  1. 安装编译依赖

    sudo apt-get install cmake libprotobuf-dev protobuf-compiler
    
  2. 克隆MNN源代码

    git clone https://github.com/alibaba/MNN
    

    原文说RangiLyu/nanodet#92用了1.0.0的版本,但是ling9601发现当时的最新版本1.1.3更快并且支持多线程,所以他用了当时最新版本1.1.3。笔者实测现在最新版本1.2.7编译会报错(可能因为后边python版本的原因没有编译成功,但是1.1.3编译出来的whl已经能够正常使用,有余力的朋友可以试着编译一下最新版本)。

    所以切换到1.1.3版本:

    git checkout 1.1.3
    
  3. 编译准备:

    cd /path/to/MNN  # 切换到MNN根目录即可
    ./schema/generate.sh
    mkdir pymnn_build
    
  4. 为python wheel的搭建搭建依赖:

    如果同时编译MNNConvert,会报下边的错误,并且没有解决方案。

    [100%] Linking CXX executable ../../MNNConvert
    /usr/bin/ld: /usr/local/lib/libprotobuf.a(arena.o): in function google::protobuf::internal::ArenaImpl::Init(bool)': arena.cc:(.text+0x3ac): undefined reference to __atomic_fetch_add_8'
    collect2: error: ld returned 1 exit status
    

    所以不编译 MNNConvert。修改下边的代码

    MNN/pymnn/pip_package/build_deps.py
    ...
     elif IS_LINUX:
         os.system('cmake -DMNN_BUILD_CONVERTER=on -DMNN_BUILD_TRAIN=ON -DCMAKE_BUILD_TYPE=Release\
             -DMNN_BUILD_SHARED_LIBS=OFF -DMNN_AAPL_FMWK=OFF -DMNN_SEP_BUILD=OFF\
             -DMNN_USE_THREAD_POOL=OFF .. && make MNN MNNTrain MNNConvert  -j4')
    ...
    

    改为:

    MNN/pymnn/pip_package/build_deps.py
    ...
        elif IS_LINUX:
            os.system('cmake -DMNN_BUILD_CONVERTER=on -DMNN_BUILD_TRAIN=ON -DCMAKE_BUILD_TYPE=Release\
                -DMNN_BUILD_SHARED_LIBS=OFF -DMNN_AAPL_FMWK=OFF -DMNN_SEP_BUILD=OFF\
                -DMNN_USE_THREAD_POOL=OFF .. && make MNN MNNTrain -j4')
    ...
    

    就是把最后的 MNNConvert删去。

    使用 build_deps.py 编译依赖:

    cd pymnn/pip_package
    python build_deps.py  
    #这一步建议在虚拟环境下运行,确保python指的是python3而不是2.7,我发现即便把该命令中的python改为python3,运行的时候,代码会自己找到2.7版本的python去编译,显示Found PythonInterp: /usr/bin/python (found version "2.7.16"),最后得到的whl文件是MNN-1.1.3-cp27-cp27m-manylinux2014_armv7l.whl而不是MNN-1.1.3-cp37-cp37m-manylinux2014_armv7l.whl,pip install直接显示不支持。
    
  5. 编译 wheel

    修改代码中的平台:

    MNN/pymnn/pip_package/build_wheel.py
    ...
        if IS_LINUX:
            os.system('python setup.py bdist_wheel --plat-name=manylinux1_x86_64')
    ...
    

    改为:

    pymnn/pip_package/build_wheel.py
    ...
        if IS_LINUX:
            os.system('python setup.py bdist_wheel --plat-name=manylinux2014_armv7l')
    ...
    # 这一步和我改的时候的代码不太一样,目前看直接改成这个plat-name就可以
    

    不能编译_tools,要把下列代码注释掉:

    pymnn/pip_package/setup.py
    ...
        tools = Extension("_tools",\
                        libraries=tools_libraries,\
                        sources=tools_sources,\
                        language='c++',\
                        extra_compile_args=tools_compile_args + extra_compile_args,\
                        include_dirs=tools_include_dirs,\
                        library_dirs=tools_library_dirs,\
                        extra_link_args=tools_extra_link_args +tools_link_args\
                            + [make_relative_rpath('lib')])
        extensions.append(tools)
    ...
    

    运行编译:

    python build_wheel.py --version 1.1.3  
    # 原文没有version参数,报错了,可能是代码发生变化了吧
    # 这一步同样虚拟环境,确保python代表python3
    # 运行的时候numpy报错了。。奇怪,但是wheel包还是生成了
    
  6. 安装wheel文件

    pip install pymnn/pip_package/dist/MNN-1.1.3-cp37-cp37m-manylinux2014_armv7l.whl
    
  7. 测试MNN包的安装

    import MNN
    

    因为没有编译 _tools,所以会出现以下报错:

    >>> import MNN
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
      File "/home/pi/.virtualenvs/mnn/lib/python3.7/site-packages/MNN/__init__.py", line 9, in <module>
        from . import tools
      File "/home/pi/.virtualenvs/mnn/lib/python3.7/site-packages/MNN/tools/__init__.py", line 1, in <module>
        from . import mnn, mnnops, mnnquant, mnnconvert 
      File "/home/pi/.virtualenvs/mnn/lib/python3.7/site-packages/MNN/tools/mnnquant.py", line 8, in <module>
        import _tools as Tools
    ModuleNotFoundError: No module named '_tools'
    

    修改python程序中的以下文件:

    /lib/python3.7/site-packages/MNN/__init__.py
    ...
    from . import tools
    ...
    

    重新测试 import MNN,没问题了

    啊啊啊啊啊啊啊啊啊啊啊啊啊成功了!!!!!!!!!啊啊啊啊啊啊啊啊啊啊啊啊啊啊啊

    推理是没有问题的,使用1920*1080的视频帧率为2 FPS,网络摄像头640*480的视频帧率为8.4 FPS,比使用yolov5n模型识别好了数十倍,yolov5n模型不管什么视频帧率都约为0.2 FPS,比ppt还卡。

    数据比较主观,可以自行实验。