前言
最近在做一个底层项目,需要用到需要用到golang调用matlab算法。
golang需要用到cgo(号称用cgo可以继承c 的半壁江山),matlab项目需要转c。golang利用cgo调用给算法传参,并得到返回结果。
虚拟机 ubuntu18
golang 1.16.10
gcc 7.5.0
备注:这个gcc版本跟golang版本是相关的,现场客户提供的gcc版本是4.9.0,我用的golang是1.14.1
项目链接:https://github.com/1486756632/cgo-emxArray_real_t
1、matlab转c
参考 https://blog.csdn.net/weixin_44982036/article/details/108657884
2、c打包成动态链接库
我以自己的测试项目为例,项目链接在上面
cd testSo
cd CarDoorPhm_DataAnalysis
gcc -fPIC -shared -o libCarDoorPhm_DataAnalysis.so CarDoorPhm_DataAnalysis.c //c文件打包成so动态链接库
你自己项目打包so文件的过程中,可能会多次报错
1、tmwtypes.h文件找不到
解决办法:把我的c项目下的文件拷贝过去就行
2、类、方法找不到,rtIsNaN、emxInit_real_T、emxInit_int32_T、emxCreateWrapperND_real_T、emxArray_real_T
解决办法:这些其实都在你的c项目,你可以把它拷贝到你的主要逻辑c文件里面,参考我的CarDoorPhm_DataAnalysis.c文件
3 golang传不定长二维数据到 c方法
头文件部分,是跟c的动态链接库相关
下图中,从上往下、从左往右,7个框
1、第一个框 声明一维数据
原因:
a、matlab没办法声明一个不定长二维数据,只能声明一个1*n的一维数组
b、算法实际需要的是一个n*15 的不定长二维数组
c、在 第三个框,调用c的emxCreateWrapper_real_T 方法,方法三个参数分别是一维数组首地址、行、列(这其实就是利用emxCreateWrapper_real_T ,声明了一个二维数组的结构体)
2、第二个框 调用c的方法
3、第七个框,是c的方法的返回数组的首地址
根据返回数组首地址,求连续17个地址的值,这17个长度的数据,就是算法的返回值
4 项目运行
cd testSo
cd CarDoorPhm_DataAnalysis
gcc -fPIC -shared -o libCarDoorPhm_DataAnalysis.so CarDoorPhm_DataAnalysis.c //c文件打包成so动态链接库
cd ../
go run main.go