C matlab引擎不启动,急,求助:实现了VS调用MATLAB引擎,但是调用MATLAB函数失败...

本帖最后由 Adel 于 2019-8-7 20:18 编辑

需要用VS调用MATLAB做数据拟合。

我已经实现了简单的VS2015调用MATLAB2018b的C和C++简单程序,见我上一篇分享帖子。其中实现的是VS调用MATLAB画图函数plot画图。

然而,现在我需要调用MATLAB中自己定义的函数(此函数还稍微有点点复杂,需要调用MATLAB的其他库函数),程序编译无误,但运行却报错指针地址读取失败(思考应该是函数调用失败)。我甚至将自己的函数写成一句一句的,每句都是MATLAB的基本语言或者库函数,还是报错内存错误。

然而调用简单的库函数是可以正确运行的。

请教高手,怎样解决?还是因为,VS调用MATLAB引擎运行MATLAB函数是有限制的,也就是我这个问题无解呢???

程序文件也粘贴在这里吧(附件虽然上传了代码文件(改后缀才能上传,都懂的——但是也不一定能看明文哦))——

TypeDefine.h

#ifndef __TYPEDEFINE_H__

#define __TYPEDEFINE_H__

#include

typedef int BOOL;

#define TRUE 1

#define FALSE 0

#endif

CruveFitting.h

#ifndef __CRUVE_FITTING_H__

#define __CRUVE_FITTING_H__

#include

#include"TypeDefine.h"

extern int CruveFitting(double inputX[],

double inputY[],

int cruveType,

BOOL isPiecewise,

int PiecewisePoint,

int firstPowerNo,

int secondPowerNo,

double relatedcoefficientR,

int parNo,

double Par[],

double concentrationVal,

double odVal,

int errorInfo);

#endif

CruveFitting.c

#include

#include

#include

#include

#include"CruveFitting.h"

#include"TypeDefine.h"

int CruveFitting(double inputX[],

double inputY[],

int cruveType,

BOOL isPiecewise,

int PiecewisePoint,

int firstPowerNo,

int secondPowerNo,

double relatedcoefficientR,

int parNo,

double Par[],

double concentrationVal,

double odVal,

int errorInfo)

{

int dataNum = 5;

int ret = 0;

Engine* eg = NULL;

if (!(eg = engOpen(NULL)))

{

printf("Open matlab enging fail!");

return 0;

}

engSetVisible(eg, true);

mxArray *X = mxCreateDoubleMatrix(1, dataNum, mxREAL);  // 创建matlab存储数据的指针

mxArray *Y = mxCreateDoubleMatrix(1, dataNum, mxREAL);

memcpy(mxGetPr(X), inputX, dataNum * sizeof(double)); // 数据复制

memcpy(mxGetPr(Y), inputY, dataNum * sizeof(double));

if ((ret = engPutVariable(eg, "X", X)) != 0)   // 把数据传递到matlab工作空间,并命名为X

printf("X:engPutVariable error:%d\n", ret);

if ((ret = engPutVariable(eg, "Y", Y)) != 0)

printf("Y:engPutVariable error:%d\n", ret);

//engEvalString(eg, "plot(x,y,'r')");// 运行绘图命令

//getchar();

mxArray *a, *b, *c;                // matlab变量的指针

a = mxCreateDoubleScalar(0);

b = mxCreateDoubleScalar(1);

c = mxCreateDoubleScalar(2);

//if ((ret = engPutVariable(eg, "a", a)) != 0)   //把数据传递到matlab工作空间,并命名为X

//        printf("a:engPutVariable error:%d\n", ret);

//if ((ret = engPutVariable(eg, "b", b)) != 0)

//        printf("b:engPutVariable error:%d\n", ret);

//if ((ret = engPutVariable(eg, "c", c)) != 0)

//        printf("c:engPutVariable error:%d\n", ret);

// 自定义MATLAB的函数原型,其中调用了MATLAB库函数fittype和fit————————————————

/*%% Gompertz model  龚帕斯模型

function[a, b, c] = Gompertz_model_fitting(x, y)

p = fittype('a*exp(-exp(b-c*x) )', 'independent', 'x');  % y = ae ^ (-e ^ (b - cx))

f = fit(x, y, p);

a = f.a;

b = f.b;

c = f.c;

% plot(f, x, y);

end*/

//—————————————————————————————————————————————————

// 方式一:直接调用函数——————————————————————————————————————

// 结果会在下面memcpy(Par, mxGetPr(b), 1 * sizeof(double)); 句报错,应该是b指针为空,实际应该是函数调用失败(猜测)

//engEvalString(eg, "[a_calc, b_calc, c_calc] = Gompertz_model_fitting(X, Y)");

//—————————————————————————————————————————————————

// 方式二:将原自定义函数改为函数体执行语句,即只调用库函数及写MATLAB基本语句————————

// 依然和上面方式报一样的错误———————————

//engEvalString(eg, "p=fittype('a*exp(-exp(b-c*x))','independent','x');");  // 调用函数

//engEvalString(eg, "f=fit(X,Y,p);");

//engEvalString(eg, "a_calc = f.a;");

//engEvalString(eg, "b_calc = f.b;");

//engEvalString(eg, "c_calc = f.c;");

// ———————————————————————————————————————————————

// 这里是测试代码,直接调用一些MATLAB的库函数,最终正确运行————————————————

engEvalString(eg, "a_calc = sum(X);");  // 调用函数

engEvalString(eg, "b_calc = sum(Y);");  // 调用函数

engEvalString(eg, "c_calc = min(X);");  // 调用函数

//———————————————————————————————————————————————

a = engGetVariable(eg,"a_calc");   //从引擎获取矩阵

b = engGetVariable(eg, "b_calc");   //从引擎获取矩阵

c = engGetVariable(eg, "c_calc");   //从引擎获取矩阵

//memcpy(Par, (double*)mxGetPr(a_calc), 1 * sizeof(double));  // 本来计划是将参数传回到Par数组中

//memcpy(Par+1, (double*)mxGetPr(b_calc), 1 * sizeof(double));

//memcpy(Par+2, (double*)mxGetPr(c_calc), 1 * sizeof(double));

//Par = mxGetPr(a);  // 测试代码,函数调用不成功,这句报错指针错误(内存错误)

//————————————————————————————————————————————————

// 在调函数时,运行到这句报错,错误见附图!

// ————————————————————————————————————————————————

memcpy(Par, mxGetPr(b), 1 * sizeof(double)); // 数据复制,

printf("b=%f\n", Par[0]);

// 测试代码

//double *p = mxGetPr(a_calc); //P指针指向矩阵的第一个元素

//printf("a=%f\n", p[0]);

//p = mxGetPr(b_calc); //P指针指向矩阵的第一个元素

//printf("b=%f\n", *p);

//p = mxGetPr(c_calc); //P指针指向矩阵的第一个元素

//printf("c=%f\n", *p);

if (eg)

{

mxDestroyArray(X);

mxDestroyArray(Y);

/*mxDestroyArray(a);

mxDestroyArray(b);

mxDestroyArray(c);*/

engClose(eg);

}

return 1;

}

main.c文件:

#include

#include

#include

#include

#include

#include"CruveFitting.h"

#include"TypeDefine.h"

int main()

{

int a = 0;

double x[5] = { 1, 1.5, 2, 2.5, 3 };

double y[5] = { 0.9, 1.7, 2.2, 2.6, 3 };

int cruveType = 1;

BOOL isPiecewise = 0;

int PiecewisePoint = 0;

int firstPowerNo = 0;

int secondPowerNo = 0;

double relatedcoefficientR = 0;

int parNo = 0;

double Par[3] = {0};

double concentrationVal = 0;

double odVal = 0;

int errorInfo = 0;

a = 2;

a = CruveFitting(x,

y,

cruveType,

isPiecewise,

PiecewisePoint,

firstPowerNo,

secondPowerNo,

relatedcoefficientR,

parNo,

Par,

concentrationVal,

odVal,

errorInfo);

printf("a=%d\n", a);

system("pause");

return 0;

}

1.png

(21.79 KB, 下载次数: 0)

2019-8-7 17:49 上传

442a53943febe9465fc072b4fbe10813.gif

b2a5a3e0dcc7d508e00275fe42fce1b5.gif

43cb6298f5f4b72a8bf2a4dd2c45d5e3.png

a70cbf5f56cb187f20fb09bae08ed3de.gif

2019-8-7 20:13 上传

点击文件名下载附件

4.51 KB, 下载次数: 2

a70cbf5f56cb187f20fb09bae08ed3de.gif

2019-8-7 20:13 上传

点击文件名下载附件

406 Bytes, 下载次数: 1

a70cbf5f56cb187f20fb09bae08ed3de.gif

2019-8-7 20:13 上传

点击文件名下载附件

803 Bytes, 下载次数: 2

a70cbf5f56cb187f20fb09bae08ed3de.gif

2019-8-7 20:13 上传

点击文件名下载附件

141 Bytes, 下载次数: 1

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值