PaddleDetection针对C#的win10平台模型部署全套流程教程(附疑难解决方案)


由于官方并没有给出Paddledetection关于C#部署的tutorial,很多第三方的教程又不够具体和详细,又或者是仅仅针对paddle 1.x的教程,缺乏时效性,本文的目的在于梳理PaddleDetection2.x关于C#的详细部署流程,以官方提供的预训练模型为例,从零开始在一台工作机上进行全流程的部署。

一. 环境配置

1.1 基础开发环境

CPU:AMD 5800 8core 16Thread
GPU : NVIDIA RTX 3090 *2
OS: Microsoft Windows10
IDE: Visual Studio 2019

1.2 软件配置环境

Git:
PortableGit-2.40.0-64-bit.7z.exe
Notepad++ (方便使用Git):
Notepad++ v8.5.1.exe
Cmake:
cmake-3.26.3-windows-x86_64.msi
OpenCV:
OpenCV – 4.7.0.exe
下载好Paddle预测库, 选择win10下的cuda11.7版本:
下载安装 Windows 推理库
在这里插入图片描述

下载好PaddleDetection的代码:选择release2.6
PaddleDetection v2.6
将上述预测库、PaddleDetection代码、opencv放在一个文件夹中:
在这里插入图片描述
CUDA11.7 和CUDNN 8.4安装教程:
PaddleX 在windows10使用paddle_inference部署C#打包dll全教程

1.3 Cmake编译

1、 首先添加环境变量,将OpenCV放置在环境变量下面
在这里插入图片描述
2、 打开Cmake软件,添加编译来源和编译输出。
编译文件来源PaddleDetection代码中deploy/cpp。作者自定义便于输出,在编译来源文件夹同一个目录下,创建了一个out文件夹:
在这里插入图片描述
在这里插入图片描述
3、点击Configure,选择x64模式

4、 出现报错、进行修改
在这里插入图片描述
5、出现报错的原因是没有进行添加相关参数的路径。分别添加cuda、opencv、预测库的路径。
在这里插入图片描述

修改后,操作1、2。可以看到生成成功,然后点击 3 Open Project会发现我们编译生成的项目。
在这里插入图片描述

Configure - > Generate -> Open Project
至此,我们成功生成了sln,下一步可以进一步修改操作:
在这里插入图片描述

1.4 在VS2019下进行调试

1、 最先选择release模式,找到main文件夹,并右键点击–重新生成
在这里插入图片描述
2、 根据错误修改。

首先我们出现了如下的报错,该错误是win32的兼容问题,需要将相关代码注掉。

在这里插入图片描述
在这里插入图片描述
另一类错误,该问题是lib库在编译时候,并没有被添加路径,需要在连接器-输入-附加依赖项中添加。
在这里插入图片描述
打开 项目 -> 链接器 -> 输入 ->附加依赖项 :
在这里插入图片描述
默认会报错找不到"./lib",把I:\Workspace\PaddleDetection_Csharp\paddle_inference\paddle\lib 下面的两个lib文件的绝对路径加入进来就可以了:

I:\Workspace\PaddleDetection_Csharp\paddle_inference\paddle\lib\libpaddle_inference.lib
I:\Workspace\PaddleDetection_Csharp\paddle_inference\paddle\lib\paddle_inference.lib
I:\Instructment\Cuda11.7\lib\x64\cudnn.lib

在这里插入图片描述

然后把默认的\cudnn.lib 这个残缺的路径补全为绝对路径:
在这里插入图片描述

再次生成解决方案,如果仍然报错,显示"setlocal"之类的,则:
在这里插入图片描述

再次生成解决方案,生成解决方案成功的信息如下:
在这里插入图片描述
得到main.exe文件:

在这里插入图片描述
生成main.exe 的目录还不能直接运行,因为缺少几个外部的.dll 库,因此需要将其复制过来:
在这里插入图片描述
在这里插入图片描述
复制到 I:\Workspace\PaddleDetection_Csharp\PaddleDetection-release-2.6\deploy\cpp\out\Release 以后,其格局如下:
在这里插入图片描述
此时可以随意运行main.exe 不报错则视为成功。
在这里插入图片描述
默认是yolov3的模型加载代码,因此在运行main.exe时给出模型路径和要推理的图片路径,即可返回一张output/output.jpg在当前目录中。

二. C#移植部署演示

以上仅仅为运行官方打包好的exe,接下来可以在官方提供的main.cc基础上进行二次开发。

2.1 修改main.cc文件(定制化)

1、首先是将外界传参改为内部自定义
2、将多有Flags全部去掉
3、在release下设置output文件夹
4、右键mian,选择设置启动项目
5、点击本地调试器得到运行结果

2.2 修改CMakeLists.txt文件

打开CMakeLists.txt文件,将原来的add_executable() 部分修改为add_librarya()
在这里插入图片描述

然后按照上文中继续重新cmake一次:
在这里插入图片描述

再次修改一遍之前的cudnn等外部静态依赖库的路径 。同时需要在属性常规配置类型中修改成动态库.dll文件,否则默认会生成如下所示的静态库.lib`文件,导致无法被C#调用。
在这里插入图片描述
在这里插入图片描述
再次运行生成解决方案,运行信息无报错,则成功:
在这里插入图片描述

2.3 C#调用打包好的dll

1.陈旧的方法往往将加载模型和图片输入都放在dll里面,并不能实现从外界传参调用。
2.C#调用原理:C#给dll传二进制流(同时得到返回值)。

2.3.1 C#窗体编写

使用vs来创建一个winform界面:

首先创建一个C#的窗体应用程序。
在这里插入图片描述
在改窗体应用程序中设置一个button事件。
在这里插入图片描述

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Runtime.InteropServices;

namespace WindowsFormsApp1
{
    
    
    public partial class Form1 : Form
    {
    
    

        int a = 3;
        int b = 2;
        public Form1()
        {
    
    
            InitializeComponent();

        }
        [DllImport("main.dll", EntryPoint = "Loadmodel", CharSet = CharSet.Ansi)]
        public static extern void Loadmodel();

        [DllImport("main.dll", EntryPoint = "add", CharSet = CharSet.Ansi)]
        public static extern int add(int a, int b);
        private void button1_Click(object sender, EventArgs e)
        {
    
    
            int c = add(a, b);
            Loadmodel();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
    
    

        }
    }
}

在这需要使用opencvsharp这个包.大家可以在工具NuGet-解决方案里面去下载.如下图所示.
在这里插入图片描述

在这里C#里面定义好图片的路径,然后C#传给C++的是一个二进制流.在C++里面有两个dll,第一个是加载模型,第二个是进行预测.两个dll被先后调用.两个dll依次被调用,目的就是能够满足只加载一次模型.

2.3.2 C#窗体调用(定制化)

接下来的操作可以根据实际项目需要定制化,随意调用dll。

1、将C++release路径下生成的文件全部复制到C#项目运行目录下,在C++的release文件中,有一些文件只有dll,没有对应的lib文件,这个时候,我们需要搜索到这些dll对应的lib文件,全部放在C#的运行目录下。(PS#这些对应的文件都在我们下载的paddle预测库中可以找到)

2、点击“启动按钮”进行测试;

3、在C#的运行目录下发现了生成了一张output.jpeg图片,证明调用成功。

三. 参考文献

[1]: PaddleDetection在windows下的部署(一)
[2]: 系列文章 如何使用PaddleDetection做一个完整项目(三)

猜你喜欢

转载自blog.csdn.net/m0_46339652/article/details/129968679