前言,C#方式---->托管和非托管
一般我们在网上一百度,就是查到托管和非托管两种方法,非托管缺陷很多,在面对接口很多的情况下,非常不好管控,同时C++的动态库还要经过繁多的extern 函数导出,破坏了面向对象的原则。
而托管的方式,可以完全保留C++原生的特性,只需要一个中间库来转化两个语言的变量即可
假设我们有一个C++dll,我们直接创建C ++动态库,这里我创建了一个QT的动态库,
请注意,如果你的C++动态库是QT类型的,托管的库也必须是QT类型的dll,qt的dll就需要根据你的库依赖,打包的时候加入Qt5Core.dll ,QWidget.dll等dll,这样C#调用的时候才不会出现 ”该dll一个或者多个依赖Not Found“ 的情况
请注意:如果你的C++库中存在使用多线程,互斥锁的情况,托管类中无法处理。请基于实际场景在C++库或者在C#的业务代码中处理
步骤1,正常创建C++dll,
步骤2,创建托管类
1.托管类设置如下,.Net版本根据具体自身业务设置
2.根据引用添加刚刚的C++dll,如果你的dll是通过nuget发布,直接右键”管理nuget程序包“—>然后搜索安装你的dll即可
这时候重点来了,C#调用时,先传入参数,在托管类Cpp中C#数据直接转成C++的参数,然后传入参数直接调用C++的接口。这里的类型要用C#的基类
如下图,如果你准备在C#中传入C#的list作为托管类这个的入参,托管类里必须使用.net平台能识别的ICollection<>,string对应的是System::String^,具体其他的大家可以自行百度或者VS中F12查看源码的基类进行尝试
3.如,我的C++里面有个ping函数,用来测试对端网络是否能连上
.h头文件
.cpp
在cpp中我把System::String^转化成了char* ,char*和std::string互相转化大家应该很熟悉了。我这个是Qt的项目把他转成了QString,然后直接调用了C++dll中的DcmExport的checkEcho方法
4.转完之后,直接调用c++/qt 的dll接口就行啦。如果涉及到回调函数和出参,道理是一样的并且均可行
步骤3,C#使用托管类
同样直接引用里添加引用即可, 这里只需要添加托管的dll即可,然后就正常调用就行啦
注意记得把dll的依赖放在托管目录同级,这样就不会依赖缺失了
注意:打包直接给别人软件直接用的的时候一定要确保其他机器有VC运行环境库,.net运行库,如果你的dll全是Debug的,还要加入编译时的VCRUNTIME140D.dll,MSVCP140D.DLL