如何将结构从 Matlab 代码转换为 C 代码(使用 Matlab 编译器)

Posted

技术标签:

【中文标题】如何将结构从 Matlab 代码转换为 C 代码(使用 Matlab 编译器)【英文标题】:How to Convert a structure from Matlab code to C code (using Matlab Compiler) 【发布时间】:2015-01-15 20:02:47 【问题描述】:

我一直在尝试使用 Matlab 编译器创建一个 C 共享库,一段时间以来,它将用作不同应用程序的插件库。我最近以为我已经完成了这项任务,只是意识到我从新的“Matlab 编译”共享库中调用的函数需要将其返回转换为 C 结构。

我使用 Matlab Answers 网站上的示例来帮助我创建包装器 level2 函数来调用需要返回结构的 Matlab 函数。(http://www.mathworks.com/matlabcentral/answers/94715-how-do-i-wrap-matlab-compiler-4-8-r2008a-created-c-dlls-to-create-another-dll)

我的问题出在下面代码的 Convert 返回的 MATLAB 数据到 C 数据 部分。我可以很好地转换为整数、双精度、字符等,但我无法弄清楚如何编写从 matlab 返回的 mxArray 到 C 结构的转换。

/* Wrapper for level 1 function exported by the MATLAB generated DLL         *
 * This function converts C data to MATLAB data, calls the MATLAB generated  *
 * function in level1.dll and then converts the MATLAB data back into C data */

int wmlfLevel1(double* input2D, int size, char* message, double** output2d)
    int nargout=1;

    /* Pointers to MATLAB data */
    mxArray *msg;
    mxArray *in2d;
    mxArray *out2d=NULL;

    /* Start MCR, load library if not done already */
    int returnval=isMCRrunning();
    if(!returnval)
        return returnval;

    /* Convert C data to MATLAB data */
    /* IMPORTANT: this has to be done after ensuring that the MCR is running */
    msg=mxCreateString(message);
    in2d=mxCreateDoubleMatrix(size, size, mxREAL);
    memcpy(mxGetPr(in2d), input2D, size*size*sizeof(double));

    /* Call the M function */
    returnval=mlfLevel1(nargout, &out2d, in2d, msg);

    /*Convert returned  MATLAB data to C data */
    *output2d=(double *)malloc(sizeof(double)*size*size);
    memcpy(*output2d, mxGetPr(out2d), size*size*sizeof(double));

    /* Clean up MATLAB variables */
    mxDestroyArray(msg);
    mxDestroyArray(in2d);
    mxDestroyArray(out2d);

    return returnval;

到目前为止,我已尝试使用 mxCreateStructMatrix 函数,我尝试创建 C 结构骨架,我即将尝试 libstruct 函数,但由于我是 C 编程和 Matlab 编译器的新手,任何帮助将不胜感激!

【问题讨论】:

【参考方案1】:

mxGetPr 只是返回一个指向双精度缓冲区的指针。 malloc 调用分配了足够的空间来存储 size^2 双打。 memcpy 正在将数据从 out2d 的内部存储复制到您的缓冲区中。

缓冲区是一维的,因此您必须根据行和列计算索引。您可以使用 output2d[col * size + row] 之类的东西来访问特定值。 (这可能会被转置 - 我现在无法访问文档。)

当你完全用完output2d 后,你需要调用free(output2d) 来释放内存,否则你的代码会有内存泄漏。

【讨论】:

谢谢凯蒂,我还有一些问题需要澄清。我是否需要更改 malloc 调用以根据类型结构分配空间,因为这是我希望存储数据的类型。我希望将我的数据从 out2d 复制到类似于下面的结构中,这将如何改变我的代码?我是否需要先设置一个 C 结构,然后使用 memcpy 将我的 out2d 数据移动到其中? '结构输出2d int variable1;双变量2;字符变量3[10]; ' 您的结构将需要空间来存储数据。如果您事先不知道size,您仍然需要malloc。 (如果您确实知道,那么您可以声明一个固定大小的二维数组。)该结构应该包含类似double* matrix 的数据元素。然后你可以做output2d.matrix = malloc(sizeof(double) * size * size)memcpy(output2d.matrix, mxGetPtr... 我用这个例子来展示我的问题,在我的代码中,我计算了一个包含 13 个数据字段的结构,其中一些只是整数,一些是数组(Matlab 中的矩阵),一个是字符串。如果我先定义结构,我会执行 output2d.element1 = malloc(sizeof(element1'stype)*size*size)), memcpy(output2d.element1,mxGetpr(out2d)... 并重复所有 13 个字段吗? Matlab 结构是动态的,使用字符串来识别字段。如果您希望 mlfLevel1 输出到结构,那么您必须反汇编 matlab 结构并将其重新组装成 C 结构。我不鼓励在这种情况下使用 malloc,试试 mxMalloc:mathworks.com/help/matlab/apiref/mxmalloc.html?refresh=true @user3528438,感谢您的提示,我继续并在必要时替换了该提示,并决定让 mlfLevel1 返回单个变量中的数据,然后将这些值分配给 C 结构。我假设这就是您拆卸 Matlab 结构并将其重新组装成 C 结构的意思。无论哪种方式,我都想办法解决我的问题,多亏了你,干杯!

以上是关于如何将结构从 Matlab 代码转换为 C 代码(使用 Matlab 编译器)的主要内容,如果未能解决你的问题,请参考以下文章

将 MATLAB 代码转换为 Python [关闭]

使用 Matlab Coder 将 Matlab m 文件转换为 C/C++ 代码,包括 mex 文件 (mxArray)

使用 Matlab Coder 将 C 字符数组转换为 Matlab 字符串

无法使用 Matlab Coder 将 Matlab 代码转换为 C 代码

如何使用 SMOP 将 Matlab 转换为 Python 代码

如何将 MATLAB 中的 detectMSERFeatures 函数转换为 C?