配置环境:
系统Windows XP,32位。
MATLAB 2011b(安装路径:D:/Program Files/MATLAB/R2011b)
VS2010 英文版(安装路径:D:/Program Files/Microsoft Visual Studio 10.0)
目的:采用由m文件构造动态链接库生成cpp文件,然后在visual studio中调用。
1. MATLAB 环境配置:
>> mbuild -setup
Welcome to mbuild -setup. This utility will help you set up
a default compiler. For a list of supported compilers, see
http://www.mathworks.com/support/compilers/R2011b/win32.html
Please choose your compiler for building standalone MATLAB applications:
Would you like mbuild to locate installed compilers [y]/n? y
(注:若是第一次mbuild -setup,选n,再在给出的的选项中选择2010 compiler,要注意安装路径是否相符)
Select a compiler:
[1] Lcc-win32 C 2.4.1 in D:\PROGRA~1\MATLAB\R2011b\sys\lcc
[2] Microsoft Visual C++ 2010 in D:\Program Files\Microsoft Visual Studio 10.0
[3] Microsoft Visual C++ 2008 SP1 in E:\Program Files\Microsoft Visual Studio 9.0
[0] None
Compiler: 2
Please verify your choices:
Compiler: Microsoft Visual C++ 2010
Location: D:\Program Files\Microsoft Visual Studio 10.0
Are these correct [y]/n? y
****************************************************************************
Warning: Applications/components generated using Microsoft Visual C++
2010 require that the Microsoft Visual Studio 2010 run-time
libraries be available on the computer used for deployment.
To redistribute your applications/components, be sure that the
deployment machine has these run-time libraries.
****************************************************************************
Trying to update options file: C:\Documents and Settings\jiao\Application Data\MathWorks\MATLAB\R2011b\compopts.bat
From template: D:\PROGRA~1\MATLAB\R2011b\bin\win32\mbuildopts\msvc100compp.bat
Done . . .
>> mex -setup
Welcome to mex -setup. This utility will help you set up
a default compiler. For a list of supported compilers, see
http://www.mathworks.com/support/compilers/R2011b/win32.html
Please choose your compiler for building MEX-files:
Would you like mex to locate installed compilers [y]/n? y
Select a compiler:
[1] Lcc-win32 C 2.4.1 in D:\PROGRA~1\MATLAB\R2011b\sys\lcc
[2] Microsoft Visual C++ 2010 in D:\Program Files\Microsoft Visual Studio 10.0
[3] Microsoft Visual C++ 2008 SP1 in E:\Program Files\Microsoft Visual Studio 9.0
[0] None
Compiler: 2
Please verify your choices:
Compiler: Microsoft Visual C++ 2010
Location: D:\Program Files\Microsoft Visual Studio 10.0
Are these correct [y]/n? y
***************************************************************************
Warning: MEX-files generated using Microsoft Visual C++ 2010 require
that Microsoft Visual Studio 2010 run-time libraries be
available on the computer they are run on.
If you plan to redistribute your MEX-files to other MATLAB
users, be sure that they have the run-time libraries.
***************************************************************************
Trying to update options file: C:\Documents and Settings\jiao\Application Data\MathWorks\MATLAB\R2011b\mexopts.bat
From template: D:\PROGRA~1\MATLAB\R2011b\bin\win32\mexopts\msvc100opts.bat
Done . . .
**************************************************************************
Warning: The MATLAB C and Fortran API has changed to support MATLAB
variables with more than 2^32-1 elements. In the near future
you will be required to update your code to utilize the new
API. You can find more information about this at:
http://www.mathworks.com/support/solutions/en/data/1-5C27B9/?solution=1-5C27B9
Building with the -largeArrayDims option enables the new API.
**************************************************************************
2.转化BoostImage.m文件
mcc -W cpplib:BoostImage -T link:lib BoostImage -d F:\zhangying\xieyulin\MatlabToC\
注:在此的m文件function最好对应end,否则容易出现 Error using mcc的错误。(但我碰到有个m文件仍不能转化成功,不知什么原因)
其中,mcc是Matlab提供的编译命令,对于这一点,Matlab的帮助说明如下:
-W lib:string link:lib其中-W是控制编译之后的封装格式,cpplib,是指编译成C++的lib,cpplib冒号后面是指编译的库的名字,
-T表示目标,link:lib表示要连接到一个库文件的目标,目标的名字是后面的BoostImage,即你写的m函数的名字。
运行完之后,你的目录下面,将会出现以下一些文件:
BoostImage.cpp
BoostImage.exp
BoostImage.dll
BoostImage.exports
BoostImage.h
BoostImage.lib
mccExcludedFiles.log
readme.txt
具体每一个文件的意思,请查帮助,这里只说其中很有用的几个:
BoostImage.dll是编译好的动态库,BoostImage这个函数封装在里面,BoostImage.h是对应的头文件,在C里面调用这个函数的时候,需要include这个头文件在这个头文件的最后,你可以看到下面的内容:
extern LIB_BoostImage_CPP_API void MW_CALL_CONV BoostImage(int nargout, mwArray& output_im, const mwArray& input_im, const mwArray& Mboost);
这就是BoostImage的C函数的声明。nargout表示输出变量的个数,a,b,c就是对应了m函数的几个变量。
注意,a,b,c三个变量的类型是mwArray,这是Matlab提供的一个特殊的变量类型(在7.0的版本,编译之后,变量类型是mxArray)。mwArray是一个类,具体可以查帮助。
4.系统环境配置
我的电脑->属性->高级->环境变量->用户变量->PATH中添加路径:D:\Program Files\MATLAB\R2011b\bin\win32,重启生效。
5.VS2010环境配置
新建一个win32 控制台应用程序,命名为MatlabTest.
右键MatlabTest解决方案->properties->VC++ Derections
(1)在“Executable Directions”项目栏,添加:D:\Program Files\MATLAB\R2011b\bin\win32(注意:当前的Mathlab安装在D:\Program Files下面)
(2)在“include Directions”项目栏,添加:D:\Program Files\MATLAB\R2011b\extern\include
(3)在“Library Directions”项目栏,添加:D:\Program Files\MATLAB\R2011b\extern\lib\win32\microsoft
上述环境只需要配置一次。
在此暂时先测试了VS2010调用matlab现有函数的功能:
1 // MatlabTest.cpp : Defines the entry point for the console application. 2 // 3 4 #include "stdafx.h" 5 #include <stdlib.h> 6 #include <stdio.h> 7 #include <string.h> 8 #include "engine.h" 9 #include "matrix.h" 10 #pragma comment(lib,"libeng.lib") 11 #pragma comment(lib,"libmx.lib") 12 int main() 13 { 14 Engine *ep; 15 int i , j ; 16 //show how to open MATLAB engine 17 //for remote ones: 18 //engOpen( ADDRESS OF REMOTE SYSTEM ) ; 19 if (!(ep = engOpen("\0"))){ 20 fprintf(stderr, "\nCan't start MATLAB engine\n"); 21 return EXIT_FAILURE; 22 } 23 //show how to create matrix 24 mxArray *Y = mxCreateDoubleMatrix(1 , 3 , mxREAL) ; 25 26 //show how to put data in matrix 27 double tmp[3] = {1.0 , 2.0 , 3.0} ; 28 memcpy(mxGetPr(Y) , tmp , sizeof(tmp)) ; 29 //show how to put variables in the Engine 30 engPutVariable(ep , "Y" , Y) ; 31 //show how to execute commands in MATLAB 32 engEvalString(ep, "X = ones(5,1) * Y"); 33 34 //show how to get variables from the Engine 35 mxArray *X = engGetVariable(ep , "X") ; 36 37 //show how to manipulate dimensions 38 int dims[10] ; 39 int ndims ; 40 ndims = mxGetNumberOfDimensions(X) ; 41 printf("total number of dimensions is %d\n" , ndims) ; 42 memcpy(dims , mxGetDimensions(X) , ndims * sizeof(int)) ; 43 for ( i = 0 ; i < ndims ; i ++ ){ 44 printf("dimension %d : %d\n" , i , dims[i]) ; 45 } 46 printf("\n") ; 47 //show how the data is stored in the memory 48 double *p = (double*)mxGetData(X) ; 49 for ( i = 0 ; i < dims[0] ; i ++ ){ 50 for ( j = 0 ; j < dims[1] ; j ++ ){ 51 printf("%8.2f" , p[j * dims[0] + i]) ; 52 } 53 printf("\n") ; 54 } 55 //---important, to release resources 56 mxDestroyArray(X) ; 57 mxDestroyArray(Y) ; 58 //show how to hide and unhide MATLAB command window 59 printf("type RETURN to hide the MATLAB command window...\n") ; 60 getchar() ; 61 engSetVisible(ep , false) ; 62 printf("type RETURN to unhide the MATLAB command window...\n") ; 63 getchar() ; 64 engSetVisible(ep , true) ; 65 printf("type RETURN to END this program...\n") ; 66 getchar() ; 67 //remembering to close it is important . 68 //but if you are debugging your programs , 69 //annotate the following line will save you a lot of time , 70 //for you needn't to restart the Engine . 71 engClose(ep) ; 72 73 //when your work is accomplished , type "exit" in MATLAB command window 74 return EXIT_SUCCESS; 75 }
运行结果:
若出现如下问题:
error C2371: 'char16_t' : redefinition; different basic types
在混合编程中,也许会出现如下错误:
—————————————————————————————————————————————————
C:Microsoft Visual Studio 10.0VCINCLUDEyvals.h(576) : error C2371: 'char16_t' : redefinition; different basic types
C:Matlabr2010aexternincludematrix.h(330) : see declaration of 'char16_t'
—————————————————————————————————————————————————
原因是VS2010中的yvals.h添加了char16_t的定义,而Matlab的matrix.h也包含对char16_t的定义,所以同时包含这两个头文件的话,会导致重复定义char16_t的错误。
解决方案:
参考:http://maciejgryka.com/bits/2011/09/char16_t-conflict-while-mexing-with-vs2010/
完全没有必要修改这两个头文件(以防修改之后,会在将来导致一些问题),只需要在包含matrix.h之前包含yvals.h即可。例如:
#include <yvals.h>
#if (_MSC_VER >= 1600)
#define __STDC_UTF_16__
#endif
#include "mex.h"
注:mex.h 包含matrix.h。这就要求我们必须知道所包含的头文件是否包含matrix.h。