使用Matalab封装动态链接库(dll)供.NET(C#)调用

时间:2024-03-14 15:48:37

我有一个梦想,是改变世界,这是很多技术人员的梦想;从小事做起,踏实做人做事,当身边的人或事因为自己能向更好的方向改变或发展的时候,那就是在改变世界,至花甲之时,可能我的梦想也无法实现,但我会一直追逐着他前行。我相信蝴蝶效应。荣耀的背后刻着一道孤独。

最近和某大学实验室团队一起处理算法工作,他们提供算法,我负责接口编写,通过调用接口,接口调用算法,从而实现算法调用以及数据持久化。他们使用matlab进行算法处理,在进行算法调用时,我们通过将算法库封装为动态链接库Dll来供C#调用从而来进行接口代码实现。算法团队提供算法源代码,我通过matlab实现可供NET调用的动态库编译及调用,并实现接口编写。
下面我们进入正题,通过书写类、函数、封装为dll,控制台调用来实现整个简单效果演示。

一、书写要编译成dll的类及函数
定义一个类
使用Matalab封装动态链接库(dll)供.NET(C#)调用

定义一个函数
使用Matalab封装动态链接库(dll)供.NET(C#)调用

构成的两个文件目录如图
使用Matalab封装动态链接库(dll)供.NET(C#)调用

二、可供C#调用的动态库dll生成
打开打包工具
在命令行窗口输入命令deploytool并回车,弹出图示打包选项,选择Library Compiler(动态库编译)
使用Matalab封装动态链接库(dll)供.NET(C#)调用

打包配置界面弹出,如图,按照图中进行配置
图中配置步骤:
1、选择动态库类别为NET程序集
2、选择要被打包成程序集的函数或类
3、指定程序集名称、描述、摘要,版本号
4、指定程序集的命名空间、类名及函数
5、选择程序集NET版本(如图中我选择的是NET4.0)
6、点击打包(Package)按钮进行打包
使用Matalab封装动态链接库(dll)供.NET(C#)调用

打包完成后,打开打包路径,即可看到打包好的可供DLL调用的动态库。
使用Matalab封装动态链接库(dll)供.NET(C#)调用

三、在NET中调用
1、安装tamlab动态库运行环境
简单原理阐述:
NET的程序要运行,需要对应或更高版本NET Framework
同理,matlab的程序也需要一个运行环境,这个运行环境是TDM-GCC(可上网搜索下载然后安装,注意根据你自身Matlab的情况使用对应的X86或X64版本)。
如何安装这里不做阐述。
2、NET中调用
新建一个控制台程序
添加相应DLL引用
(1)你编译好的程序集
(2)MWArray.dll(该Dll在你安装完运行环境后,使用Everything工具搜索即可获取)
如图,我把两个dll拷贝并添加到了项目中,同时在引用中添加了引用
使用Matalab封装动态链接库(dll)供.NET(C#)调用

MWArray.dll可以把它理解为一个转换器(类似我们NET中的公共类型库和公共运行语言),他能实现NET中数据类型与Matlab生成的Dll的类型的互转等。

此时,我们就可以实现动态库的使用了。如图(如图你会发现,运行首次调用动态库的函数会比较慢,你再看看内存,你会发现内存瞬间会飙升,是因为首次调用的时候,会启动TDM-GCC运行环境;所以在调用设计的时候,可以采用单例设计模式或更优的其他方式来保证算法调用的一些效率及性能问题)
使用Matalab封装动态链接库(dll)供.NET(C#)调用

结果:函数直接可以按照我们NET中的理解来调用,但是类不可以调用(Matlab中的类被封装成了一个NET中的函数)

疑问:封装的类也会变成一个函数,并不会被编译为我们NET中理解的类(NET中的类包含函数可调用),所以从调用结果中可以看出,Test类只能被当做一个NET中的一个函数来使用,这是我的一个疑惑,是否真的是这样,就目前的实验结果来看,是这样的;有可能有方式可以实现,但是我并没有再做深入,如果小伙伴有觉得不对的地方可以指出一起讨论,欢迎评论。

注意:项目的运行平台(x86或x64要注意,如果matlab是x64的,那么要记得调用动态库的宿主或控制台尽量是x64)
我遇到过这样的情况,x64的matlab生成的动态库,WCF调用算法动态库,wcf服务寄宿在IIS上可以正常调用动态库,但是在调试环境下,直接运行wcf服务无法正常调用,但是将wcf服务寄宿在x64的控制台上即可正常调用。

综上所述,我们已经实现了Matlab封装DLL供NET调用的整个过程。