瑞芯微Rockchip开发者社区
直播中

duke刘

9年用户 705经验值
擅长:可编程逻辑
私信 关注
[问答]

YOLOv5s算法在RK3399ProD上的部署推理流程是怎样的

YOLOv5s算法在RK3399ProD上的部署推理流程是怎样的?基于RK33RK3399Pro怎样使用NPU进行加速推理呢?

回帖(1)

常静娜

2022-2-11 13:48:41
1. 部署流程



  • 在服务器端或者电脑端进行训练,训练完成后将.pt文件转换成ONNX格式
  • 电脑端使用rknn-toolkit1.6.0将ONNX模型转换成RKNN模型
  • RK3399Pro中进行模型推理
  其中第二步,转换模型,可以在装了rknn-toolkit的rk3399Pro中,之前不知道的时候都是在这个开发板中进行转换的,不过还是建议在电脑端Ubuntu18.04系统下进行转换,可以将量化的batch设置的大一些,量化的速度快一些。
  2. 环境准备


  环境问题可能是比较棘手的问题,因为好多人都是在这个问题上出现了各种各样的bug,最好的办法是直接在Ubuntu上拉取他们提供的docker,直接拉取,环境都给配置好了,然后转换模型。
然后开发板选择官方的开发板,官方的开发板环境是最友好的,官方的RK3399Pro里面给安装好了环境,不怎么需要配置环境,不怎么会遇到问题,用于算法的验证还是很好的。
接下来是我在Ubuntu上配置的环境(使用的比较笨的方法QAQ),该环境是根据RKNN提供的手册进行安装的,其中,想要安装最终的rknn-toolkit1.6.0及以上版本,需要提前安装好依赖库,并且依赖库的版本要求非常的严格,版本不能有任何的不一样,在Rockchip_Quick_Start_RKNN_Toolkit_V1.6.1_CN.pdf文件中。
在Ubuntu上,我安装的是3.6版本的Python,其余的环境是按照下面的库依赖,严格配置的。安装好依赖库之后,去rockchip的官方仓库下载编译好的whl文件,直接在环境中pip install + xxx.whl就行了

  



  3. 服务器端或者电脑端训练YOLOv5s



训练这部分并不用多说什么,仓库拉出来,根据自己的数据集改好参数,然后进行训练,YOLOv5的训练还是挺友好的。
  不过训练YOLOv5的过程中,我选择在common文件中,将silu层全部换成了RuLe层,因为对准换后的RKNN模型有加速作用,这样总体的mAP会稍微降一些,经过测试总体的mAP降低的。

Rockchip_Developer_Guide_RKNN_Toolkit_Custom_OP_V1.6.1_CN.pdf在该文件中有详细的解释,使用ReLU激活层会融合一些层,从而进行优化。
  4. 模型转换—>ONNX

根据github项目需要先将PyTorch训练出的.pt模型转换成ONNX格式。根据项目的Repo直接转换即可。
在命令行输入 :
python3 models/export_op.py --rknn_mode 即可。
  5. 模型转换—>RKNN

将转换出来的模型xxxx.onnx复制到convert文件夹下面,convert文件夹需要有转换脚本,dataset.txt的量化文件,量化图片。量化的图片建议200张,batch尽量设置的大一些。
在命令行输入:


import yaml

from rknn.api import RKNN

import cv2



_model_load_dict = {

    'caffe': 'load_caffe',

    'tensorflow': 'load_tensorflow',

    'tflite': 'load_tflite',

    'onnx': 'load_onnx',

    'darknet': 'load_darknet',

    'pytorch': 'load_pytorch',

    'mxnet': 'load_mxnet',

    'rknn': 'load_rknn',

    }



yaml_file = './config.yaml'





def main():

    with open(yaml_file, 'r') as F:

        config = yaml.load(F)

    # print('config is:')

    # print(config)



    model_type = config['running']['model_type']

    print('model_type is {}'.format(model_type))#检查模型的类型



    rknn = RKNN(verbose=True)







#配置文件

    print('--> config model')

    rknn.config(**config['config'])

    print('done')





    print('--> Loading model')

    load_function = getattr(rknn, _model_load_dict[model_type])

    ret = load_function(**config['parameters'][model_type])

    if ret != 0:

        print('Load yolo failed! Ret = {}'.format(ret))

        exit(ret)

    print('done')



    ####

    #print('hybrid_quantization')

    #ret = rknn.hybrid_quantization_step1(dataset=config['build']['dataset'])





    if model_type != 'rknn':

        print('--> Building model')

        ret = rknn.build(**config['build'])

        print('acc_eval')

        rknn.accuracy_analysis(inputs='./dataset1.txt', target='rk3399pro')

        print('acc_eval done!')



        if ret != 0:

            print('Build yolo failed!')

            exit(ret)

    else:

        print('--> skip Building model step, cause the model is already rknn')





#导出RKNN模型

    if config['running']['export'] is True:

        print('--> Export RKNN model')

        ret = rknn.export_rknn(**config['export_rknn'])

        if ret != 0:

            print('Init runtime environment failed')

            exit(ret)

    else:

        print('--> skip Export model')





#初始化

    print('--> Init runtime environment')

    ret = rknn.init_runtime(**config['init_runtime'])

    if ret != 0:

        print('Init runtime environment failed')

        exit(ret)

    print('done')





    print('--> load img')

    img = cv2.imread(config['img']['path'])

    print('img shape is {}'.format(img.shape))

    img = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)

    inputs = [img]

    print(inputs[0][0:10,0,0])

#推理

    if config['running']['inference'] is True:

        print('--> Running model')

        config['inference']['inputs'] = inputs

        #print(config['inference'])

        outputs = rknn.inference(inputs)

        #outputs = rknn.inference(config['inference'])

        print('len of output {}'.format(len(outputs)))

        print('outputs[0] shape is {}'.format(outputs[0].shape))

        print(outputs[0][0][0:2])

    else:

        print('--> skip inference')

#评价

    if config['running']['eval_perf'] is True:

        print('--> Begin evaluate model performance')



其中在设置config部分的参数时,建议看看官方的API介绍,去选择相应的参数部分,在文件Rockchip_User_Guide_RKNN_Toolkit_V1.6.1_CN.pdf
  6. RK3399Pro中模型推理

在detect文件夹下,其中data/image下面放的是需要检测的图片,在models文件夹下放的是转换的RKNN模型

最后点开shell 执行:
python rknn_detect_for_yolov5_original.py 即可
在开发板中会生成模型推理的结果和时间

推理的时间比较快,60毫秒左右,这个推理速度和我在笔记本电脑(3060)上使用模型detect的速度是差不多的。
  7.模型预编译

解决模型的加载时间过长的问题



from rknn.api import RKNN
if __name__ == '__main__':
    # Create RKNN object
    rknn = RKNN()
# Load rknn model
ret = rknn.load_rknn('./best_as_200.rknn')
if ret != 0:
    print('Load RKNN model failed.')
    exit(ret)
# init runtime
ret = rknn.init_runtime(target='rk3399pro', rknn2precompile=True)
if ret != 0:
    print('Init runtime failed.')
    exit(ret)
# Note: the rknn2precompile must be set True when call init_runtime
ret = rknn.export_rknn_precompile_model('./best_pre_compile.rknn')
if ret != 0:
    print('export pre-compile model failed.')
    exit(ret)
rknn.release()


  转换的环境是在RK3399Pro中,方法很笨但是有效。
将生成的模型继续使用模型的推理代码,在RK3399Pro中进行预测,模型推理速度50毫秒左右,有20FPS,使用Python接口还是比较快的了。
  
举报

更多回帖

发帖
×
20
完善资料,
赚取积分