|
Sir,
I don't understand this error message. You should not be compiling .m files using the MatlabEngine ??? Are you trying to do .mex files ?
ps: Please encapsulate your error message in pre tags and do a full cut-and-paste of the compilation log!
Jonathan de Halleux.
www.dotnetwiki.org
|
|
|
|
|
Hello! I'm soo happy there is code to make it able to run Matlab from C++.
I'm having a camera with a C++ program. I need to do things to my camera-images and find it easiest to do it in Matlab. So I've understood that in my C++ code I could just add the MatlabEngine.h and .cpp -files (and StdAfx files) to my project, include MatlabEngine.h to my C++ code, initialize and unitialize the engine and inbetween perform whatever I like to perform, correct?
My problem is that if I only do CoInitialize(NULL), then Matlab doesn't get initialized, so if I add "mt=new CMatlabEngine;" then my program warns me saying that I bool to false or true, but I can run the program, just not perform anything if I would like to. What can I have missed?
[ONE HOUR LATER: I took out CoInitialize(NULL) and now I could run PutString(). So is it good enough just having "mt=new CMatlabEngine;" to initialize Matlab?]
I can run the demo without problems, BUT you have written "/TODO: Place code here" in int APIENTRY WinMain(..) in the MatlabEngineDemo.cpp file, and I understood that line as to write some code afterwards, and I tried it, but with no results at all. I added the three lines for PutString as you have later on. What's the meaning here? should I add code or not and what kind of code could I add?
Merci bcp
|
|
|
|
|
astridwahlin wrote:
[ONE HOUR LATER: I took out CoInitialize(NULL) and now I could run PutString(). So is it good enough just having "mt=new CMatlabEngine;" to initialize Matlab?]
This should be sufficient. You don't need to call CoInitialize(NULL) if the COM interface is already initialized. Note that are not obliged to allocated dynamically CMatlabEngine.
astridwahlin wrote:
"/TODO: Place code here"
This is generated by the MFC wizard. You should modify the code at this point but add new code in the WndProc function.
Don't bother about modifying the demo version (which is for demonstration), I advise you to create a new console application and start from scratch: create an empty console project, follow the article for that.
Jonathan de Halleux.
www.dotnetwiki.org
|
|
|
|
|
I integrated this class into a simulator that makes many calls to the CMatlabEngine::Execute() function.
Memory usage of the program increased tremendously.
I think that this is caused by m_vResult, which gets the return value from matlab.
This variable is also used in IsVisible() and GetString().
Must it be explicitly freed before reusing (I'm not too familiar with VARIANT types)?
|
|
|
|
|
This is what I did to solve the memory leaks, but I haven't debugged this much to see if it causes any damage:
In MatlabEngine.h, I added a protected method:
void FreeResult();
In MatlabEngine.cpp I made the following changes:
In the constructor, added:
m_vResult.bstrVal = NULL;
Before every call to
m_pMtlbDispApp ->Invoke(..., &m_vResult, ...)
(there are three such calls, in Execute(), IsVisible() and GetString())
I added:
FreeResult();
At the end of the file I added:
void CMatlabEngine::FreeResult()
{
if (m_vResult.vt == VT_BSTR) {
::SysFreeString(m_vResult.bstrVal);
m_vResult.bstrVal = NULL;
}
}
I would be happy to hear any remarks - if there is anything else that must be checked before freeing the result, or if there is anything else to initialize.
Hope this helps more than it hurts,
- Arnon
|
|
|
|
|
I'll have look.
Jonathan de Halleux.
|
|
|
|
|
It seems like there are two small bugs in the error handler:
1. ::_tprintf should be ::_stprintf (lines 136 and 155), otherwise, the error strings errMsg and extMess are left as garbage.
2. errDesc is used without being set (line 138).
Where can you find the description of the error message?
Thanks,
- Arnon
|
|
|
|
|
I made some changes to the error handler so that I could see a description of the MATLAB errors that I get. Here is my modified version of ErrHandler:
<code>
void CMatlabEngine::ErrHandler(HRESULT hr, EXCEPINFO excep, UINT uArgErr)
{
USES_CONVERSION;
if (hr == DISP_E_EXCEPTION)
{
TCHAR errMsg[512];
::_stprintf(errMsg, TEXT("Run-time error %d:\n\n %s"),
excep.scode & 0x0000FFFF,
OLE2T(excep.bstrDescription));
::MessageBox(NULL, errMsg, TEXT("MATLAB Error"),
MB_SETFOREGROUND | MB_OK);
}
else
{
LPVOID lpMsgBuf;
::FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER |
FORMAT_MESSAGE_FROM_SYSTEM |
FORMAT_MESSAGE_IGNORE_INSERTS, NULL, hr,
MAKELANGID(LANG_NEUTRAL,
SUBLANG_DEFAULT),(LPTSTR) &lpMsgBuf,
0, NULL);
if ((hr == DISP_E_TYPEMISMATCH ) ||
(hr == DISP_E_PARAMNOTFOUND))
{
TCHAR extMess[512];
::_stprintf(extMess, TEXT("%s Position of incorrect argument is %u.\n"), (LPCTSTR) lpMsgBuf, uArgErr);
::MessageBox(NULL, extMess, TEXT("COM Error"), MB_OK | MB_SETFOREGROUND);
}
else
{
::MessageBox(NULL, (LPCTSTR)lpMsgBuf, TEXT("COM Error"),MB_OK | MB_SETFOREGROUND);
}
::LocalFree(lpMsgBuf);
}
}
</code>
You must also add the following line to MatlabEngine.cpp:
<code>
#include <atlbase.h>
</code>
|
|
|
|
|
Thank you for the fix. I'll post an update of the source but it will take time to get to CP.
Jonathan de Halleux.
|
|
|
|
|
Thanks for this simple and very useful class.
The beautifully formatted doxygen documentation could be used as a reference for most programmers to learn from...
One small issue and one question:
In the article, you recommend checking IsInitialized() after instantiating the class, but you don't do this in the demo code.
And for the question:
We have a limited number of licenses at work. When you open matlab but can't get a license, you get a fatal error message box, and after you close it, matlab closes. Unfortunately, IsInitialized() returns true even when a license wasn't acquired. Is there any way to make sure that the app was really opened?
|
|
|
|
|
This is what I added to the demo code in InitInstance:
<br />
glob_pMatlab = new CMatlabEngine;<br />
if (!glob_pMatlab->IsInitialized()) {<br />
::MessageBox(NULL,"Can't initialize MATLAB","Fatal Error!",MB_OK);<br />
return FALSE;<br />
}
|
|
|
|
|
Thks (don't forget to vote )
arnonm wrote:
In the article, you recommend checking IsInitialized() after instantiating the class, but you don't do this in the demo code.
In fact, I'll fix that in the next release. Anyway, all methods of the wrapper check if it is initialized too...
arnonm wrote:
We have a limited number of licenses at work. When you open matlab but can't get a license, you get a fatal error message box, and after you close it, matlab closes. Unfortunately, IsInitialized() returns true even when a license wasn't acquired. Is there any way to make sure that the app was really opened?
You too... This damn software is not cheap and has a "very" dominant position on the math field.
I'm not very much into COM now... The key of the problem is "how to know if Matlab is open or not ???"
Anybody an idea?
Jonathan de Halleux.
|
|
|
|
|
Is the sample available in C#?
This sample works, but when I add the Reference in a Project and call mlapp.Execute("..."); I get the exception QueryInterface for interface MLapp.DIMLapp failed.
Why?
Laszlo Sragner
|
|
|
|
|
sragner wrote:
Is the sample available in C#?
No, you can write it...
sragner wrote:
when I add the Reference in a Project and call mlapp.Execute(".
? what do you mean ?
Jonathan de Halleux.
|
|
|
|
|
My filter is a sixth order bessel low pass filter.
Here is the matlab code.
function filter
clear all;
a=[10395];
wo=1/(23.43e6)
b=[1*(wo^6) 21*(wo^5) 210*(wo^4) 1260*(wo^3) 4725*(wo^2) 10395*(wo) 10395];
c=tf(a,b)
h=c2d(c,1/52.32e6,'tustin')
bode(h)
I wrote the same code in VC++
/*******************************************************************************************
Transfer function:
10395
---------------------------------------------------
6.045e-045 s^6 + 2.974e-036 s^5 + 6.968e-028 s^4
+ 9.796e-020 s^3 + 8.607e-012 s^2
+ 0.0004437 s + 10395
Transfer function:
0.02651 z^6 + 0.1591 z^5 + 0.3977 z^4 + 0.5302 z^3
+ 0.3977 z^2 + 0.1591 z + 0.02651
---------------------------------------------------
z^6 + 0.1852 z^5 + 0.4568 z^4 + 0.01633 z^3
+ 0.03876 z^2 - 0.0007527 z + 0.0003637
Sampling time: 1.9113e-008
********************************************************************************************/
unsigned char bessel(unsigned char x) // Function accessible only from this file
{
double b0=0.02651,b1=0.1591,b2=0.3977, b3=0.5302, b4=0.3977, b5=0.1591, b6=0.02651;
double a1= -0.1852, a2= -0.4568, a3= -0.01633, a4= -0.03876, a5= 0.0007527, a6= -0.0003637;
double temp_x1,temp_x2,temp_x3,temp_x4,temp_x5,temp_x6,temp_x7;
double temp_y1,temp_y2,temp_y3,temp_y4,temp_y5,temp_y6;
double y;
unsigned char y_unsigned;
double static xn_1,xn_2,xn_3,xn_4,xn_5,xn_6;
double static yn_1,yn_2,yn_3,yn_4,yn_5,yn_6;
temp_x1 = x * b0;
temp_x2 = xn_1* b1;
temp_x3 = xn_2 * b2;
temp_x4 = xn_3 * b3 ;
temp_x5 = xn_4 * b4;
temp_x6 = xn_5 * b5;
temp_x7 = xn_6 * b6;
temp_y1 = yn_1 * a1;
temp_y2 = yn_2* a2;
temp_y3 = yn_3 * a3;
temp_y4 = yn_4 * a4 ;
temp_y5 = yn_5 * a5;
temp_y6 = yn_6 * a6;
y = temp_x1 + temp_x2 + temp_x3 + temp_x4 + temp_x5 + temp_x6 + temp_x7 + temp_y1 + temp_y2 + temp_y3 + temp_y4 + temp_y5 + temp_y6 ;
xn_6 = xn_5;
xn_5 = xn_4;
xn_4 = xn_3;
xn_3 = xn_2;
xn_2 = xn_1;
xn_1 = (double) x;
yn_6 = yn_5;
yn_5 = yn_4;
yn_4 = yn_3;
yn_3 = yn_2;
yn_2 = yn_1;
yn_1 = y;
y_unsigned = (unsigned char) y;
return y_unsigned;
}
I am working with an experimental platform and filtering is one of the applications of it.
What i am looking for,is to get my matlab plot function when i run the code,after i have done suitable routine and created libraries( you are the specialist).
I hope i'am not too confusing.Please let me know if you need more explanation,or i can send you my code to check if you have some time.
From you name,i can deduce you might be a french speaker
Thx
F.K
|
|
|
|
|
flora_k wrote:
I wrote the same code in VC++
Where is it ?
flora_k wrote:
you might be a french speaker
Yes indeed.
Btw, you're bessel function looks strange to me: you are usingt a lot of uninitialized parameters;..
Jonathan de Halleux.
|
|
|
|
|
I put the code on the previous message. i just copy/paste it.
All the parameters have been initialized. i think it's a good idea i give you the insight of the whole thing. There we go
// CPPAnalyzerTestModule.cpp : Implementation of CPPAnalyzerTestModule
#include "stdafx.h"
#include "PPAnalyzerTestModule.h"
#include "CPPAnalyzerTestModule.h"
#include "StrDef.h"
// for filter function
#include <stdio.h>
#include <math.h>
//for matlab interfacing
#include <engine.h>
#include "myfunctions.h"
#define BUFSIZE 256
Engine*ep;
mxArray *A_ptr;
double *A;
/////////////////////////////////////////////////////////////////////////////
// CPPAnalyzerTestModule
// handlers used by this module
PPHANDLER_IMPLEMENT_USAGE(PPLogHandler)
PPHANDLER_IMPLEMENT_USAGE(PPErrorHandler)
// imported command id's from other module classes to use PPCMD() macros
#define IMPORT_MODULECOMMANDS
#include "PPChainLib\CmdMap.h"
#include "PPProxyLib\CmdMap.h"
/* TODO: Add #includes for other module classes used:
#include "PPSomeModule\CmdMap.h"
#include "PPOtherModule\CmdMap.h"
... or delete the entire IMPORT_MODULECOMMANDS section if not needed */
#undef IMPORT_MODULECOMMANDS
// function prototypes
void Filter(long amount, unsigned char* pData);
unsigned char bessel(unsigned char x);
// -------------------------------------------------------
// CONSTRUCTOR/DESTRUCTOR
//##ModelId=3B6171AE006E
CPPAnalyzerTestModule::CPPAnalyzerTestModule()
{
PPHANDLER_START_USAGE(PPLogHandler)
PPHANDLER_START_USAGE(PPErrorHandler)
PPLOG2(COARSE, CHAINMODULES, INF, STR_STARTUP, GetModuleClassName())
InitMatlab();
}
//##ModelId=3B6171AE006F
CPPAnalyzerTestModule::~CPPAnalyzerTestModule()
{
PPLOG2(COARSE, CHAINMODULES, INF, STR_SHUTDOWN, GetModuleClassName())
PPHANDLER_STOP_USAGE(PPErrorHandler)
PPHANDLER_STOP_USAGE(PPLogHandler)
CloseMatlab();
}
// -------------------------------------------------------
// PUBLIC COM INTERFACE METHODS
STDMETHODIMP CPPAnalyzerTestModule::Reset(int *result)
{
// keep functionality of baseclass
return CPPChainModuleBase::Reset(result);
}
//##ModelId=3B6171AE007A
STDMETHODIMP CPPAnalyzerTestModule::SetChainModuleId(long idModule, int *result)
{
// keep functionality of baseclass
return CPPChainModuleBase::SetChainModuleId(idModule, result);
}
//##ModelId=3B6171AE007E
STDMETHODIMP CPPAnalyzerTestModule::Connect(unsigned inputNr, IPPChainModule* pPrevModule, unsigned prevOutputNr, int *result)
{
// keep functionality of baseclass
return CPPChainModuleBase::Connect(inputNr, pPrevModule, prevOutputNr, result);
}
//##ModelId=3B6171AE008C
STDMETHODIMP CPPAnalyzerTestModule::SetParameter(IUnknown* pIUnk, int* result)
{
// extend functionality of baseclass
// following file implements the moduleparameter dispatch switch
#include "ParMap.h"
}
//##ModelId=3B6171AE0091
STDMETHODIMP CPPAnalyzerTestModule::SetCommand(long idDest, long idCmd, __int64 offset, const unsigned char* pData, long amount, int* result)
{
// keep functionality of baseclass
return CPPChainModuleBase::SetCommand(idDest, idCmd, offset, pData, amount, result);
}
//##ModelId=3C6D24A501D3
STDMETHODIMP CPPAnalyzerTestModule::IsEnabled(int *IsEnabled, int *ModuleName, int *result)
{
// keep functionality of baseclass
return CPPChainModuleBase::IsEnabled(IsEnabled, ModuleName, result);
}
//##ModelId=3B6171AE009F
STDMETHODIMP CPPAnalyzerTestModule::Validate(int* result)
{
// extend functionality of base class
*result = PP_OK;
HRESULT hr = CPPChainModuleBase::Validate(result);
if (SUCCEEDED(hr) && (*result == PP_OK))
{
// TODO: Add code here for further validation
}
return hr;
}
//##ModelId=3B6171AE00A9
STDMETHODIMP CPPAnalyzerTestModule::Prepare(int* result)
{
// extend functionality of base class
*result = PP_OK;
HRESULT hr = CPPChainModuleBase::Prepare(result);
if (SUCCEEDED(hr) && (*result == PP_OK))
{
}
return hr;
}
//##ModelId=3B6171AE00AC
STDMETHODIMP CPPAnalyzerTestModule::Run(int* result)
{
// keep functionality of baseclass
return CPPChainModuleBase::Run(result);
}
//##ModelId=3C8F773300EF
STDMETHODIMP CPPAnalyzerTestModule::HandleEvent(eModuleEventType eventType, int * result)
{
// keep functionality of baseclass
return CPPChainModuleBase::HandleEvent(eventType, result);
}
//##ModelId=3B6171AE00AF
STDMETHODIMP CPPAnalyzerTestModule::Pull(unsigned outputNr, long amount, long *amountActual, unsigned char* pData, unsigned char * ppCmds, int *more, int *result)
{
HRESULT hr = S_OK;
// replace functionality of baseclass
PullEntry(outputNr, amount, amountActual, pData, ppCmds, more, result);
if (*result == PP_OK)
{
// the main thing: read from previous module
hr = PullPrevModule(0, amount, amountActual, pData, ppCmds, more, result);
if (SUCCEEDED(hr) && (*result == PP_OK))
{
// command preprocessing
PullTransposeCmds(ppCmds, amountActual, pData); // TODO: override if necessary
PullInsertCmds(ppCmds, amountActual, pData);
// a basic loop for command processing
CCmdIterator iter(ppCmds);
CCommand *pCmd;
while (!iter.Ready() && (*result == PP_OK) && *more)
{
if ((pCmd = iter.GetNextCmdForMe(GetChainModuleId())) != NULL)
{
HandleCommand(pCmd, amountActual, pData, more, result);
if (!pCmd->IsBroadcastCmd())
delete pCmd;
}
}
}
/*
Process the data in this block
*/
// call your function
// use number of samples (amount actual)
// use buffer :
// yourfunc(long samples, unsigned char* pData);
//DisplayMatlab(*amountActual, pData, 0);
//FilterInMatlab(*amountActual, pData);
//either
//Filter(*amountActual, pData);
DisplayMatlab(*amountActual, pData, 1);
/*
Process the data in this block
*/
}
PullExit(outputNr, amount, amountActual, pData, ppCmds, more, result);
return hr;
}
//##ModelId=3BB850280291
STDMETHODIMP CPPAnalyzerTestModule::GetRunTimeInfo(const char* name, char* value, int maxlen, int* result)
{
// extend functionality of baseclass
// following file implements the runtimeinfo dispatch switch
#include "RtiMap.h"
}
STDMETHODIMP CPPAnalyzerTestModule::LogDumpRunTimeInfo(int* result)
{
// extend functionality of baseclass
// following lines implement the logdump of all runtimeinfo
#define LOGDUMP_MODULERUNTIMEINFO
#include "RtiMap.h"
#undef LOGDUMP_MODULERUNTIMEINFO
}
//##ModelId=3B61838B030A
STDMETHODIMP CPPAnalyzerTestModule::Abort(int* result)
{
// keep functionality of baseclass
return CPPChainModuleBase::Abort(result);
}
// -------------------------------------------------------
// OVERRIDEABLE METHODS
//##ModelId=3B6171AE0070
const char *CPPAnalyzerTestModule::GetModuleClassName() const
{
// override functionality of baseclass
return STR_MODULECLASSNAME;
}
//##ModelId=3BF1480F01AA
void CPPAnalyzerTestModule::HandleCommand(CCommand *pCmd, long *amountActual, unsigned char *pData, int* more, int *result)
{
// extend functionality of baseclass
// following file implements the commandhandler dispatch switch
#include "CmdMap.h"
}
// -------------------------------------------------------
// MODULEPARAMETER METHODS
// TODO: replace with your own module parameters
//##ModelId=3B6171AE00C9
int CPPAnalyzerTestModule::SetExampleParam(long value)
{
if (value < 0) // is just an example
{
PPERROR2(STR_ERR_EXAMPLEPARAM, GetModuleClassName())
PPLOG2(COARSE, CHAINMODULES, ERR, STR_ERR_EXAMPLEPARAM, GetModuleClassName())
return PP_NOT_OK;
}
m_ExampleParam = value;
return PP_OK;
}
// -------------------------------------------------------
// MODULERUNTIMEINFO METHODS
// TODO: replace with your own module runtime info
//##ModelId=3BF1480F00DF
int CPPAnalyzerTestModule::GetExampleInfo(char* value, int maxlen) const
{
// return example info
static long exampleInfo = 0;
_snprintf(value, maxlen, "ExampleInfo: %ld", exampleInfo++); // is just an example
return PP_OK;
}
// -------------------------------------------------------
// MODULECOMMAND METHODS
// TODO: replace with your own module commands
//##ModelId=3BF1480F01D9
int CPPAnalyzerTestModule::HandleSetByteExample(CCommand *pCmd, long *amountActual, unsigned char *pData, int* more)
{
// set byte to 0xee on offset location
pData[pCmd->GetOffset()] = 0xee; // is just an example
return PP_OK;
}
/*******************************************************************************************
Transfer function:
10395
---------------------------------------------------
6.045e-045 s^6 + 2.974e-036 s^5 + 6.968e-028 s^4
+ 9.796e-020 s^3 + 8.607e-012 s^2
+ 0.0004437 s + 10395
Transfer function:
0.02651 z^6 + 0.1591 z^5 + 0.3977 z^4 + 0.5302 z^3
+ 0.3977 z^2 + 0.1591 z + 0.02651
---------------------------------------------------
z^6 + 0.1852 z^5 + 0.4568 z^4 + 0.01633 z^3
+ 0.03876 z^2 - 0.0007527 z + 0.0003637
Sampling time: 1.9113e-008
********************************************************************************************/
unsigned char bessel(unsigned char x) // Function accessible only from this file
{
double b0=0.02651,b1=0.1591,b2=0.3977, b3=0.5302, b4=0.3977, b5=0.1591, b6=0.02651;
double a1= -0.1852, a2= -0.4568, a3= -0.01633, a4= -0.03876, a5= 0.0007527, a6= -0.0003637;
double temp_x1,temp_x2,temp_x3,temp_x4,temp_x5,temp_x6,temp_x7;
double temp_y1,temp_y2,temp_y3,temp_y4,temp_y5,temp_y6;
double y;
unsigned char y_unsigned;
double static xn_1,xn_2,xn_3,xn_4,xn_5,xn_6;
double static yn_1,yn_2,yn_3,yn_4,yn_5,yn_6;
temp_x1 = x * b0;
temp_x2 = xn_1* b1;
temp_x3 = xn_2 * b2;
temp_x4 = xn_3 * b3 ;
temp_x5 = xn_4 * b4;
temp_x6 = xn_5 * b5;
temp_x7 = xn_6 * b6;
temp_y1 = yn_1 * a1;
temp_y2 = yn_2* a2;
temp_y3 = yn_3 * a3;
temp_y4 = yn_4 * a4 ;
temp_y5 = yn_5 * a5;
temp_y6 = yn_6 * a6;
y = temp_x1 + temp_x2 + temp_x3 + temp_x4 + temp_x5 + temp_x6 + temp_x7 + temp_y1 + temp_y2 + temp_y3 + temp_y4 + temp_y5 + temp_y6 ;
xn_6 = xn_5;
xn_5 = xn_4;
xn_4 = xn_3;
xn_3 = xn_2;
xn_2 = xn_1;
xn_1 = (double) x;
yn_6 = yn_5;
yn_5 = yn_4;
yn_4 = yn_3;
yn_3 = yn_2;
yn_2 = yn_1;
yn_1 = y;
y_unsigned = (unsigned char) y;
return y_unsigned;
}
void Filter (long amount, unsigned char* pData)
{
long n;
unsigned char y;
for (n=0; n
|
|
|
|
|
What is your question / problem ?
Jonathan de Halleux.
|
|
|
|
|
Hello,
Here is my problem; i have a working program in matlab,say a filter. I have a ready made program in VC++ .What i want to do is to call and display my matlab filter in the VC++ code without actually opening a matlab window.
Is this possible with you theory?
I tried the source code, but there seems to be a problem, i keep having errors.
Help please
F.K
|
|
|
|
|
flora_k wrote:
What i want to do is to call and display my matlab filter in the VC++ code without actually opening a matlab window.
What do you mean exactly ?
flora_k wrote:
I tried the source code, but there seems to be a problem, i keep having errors.
If you don't give more details, I can't do much. Moreover, I've unsinstalled matlab so I won't be of any help.
Jonathan de Halleux.
|
|
|
|
|
Hello,
For the sample program to be provided, could you please indicate which header files and libraries( and their path as well) have to be included in order for the program to be compiled properly?
F.K
|
|
|
|
|
The files provided in the "source file" zip.
Jonathan de Halleux.
|
|
|
|
|
Hi again,
My question may sound silly,i am new in this. What is the relation ship between your theory and the matlab engine? What i mean is i can not see the C engine routine in your code.
Could you please provide sample of working code with your approach of the problem?
Thx
F.K
|
|
|
|
|
There is no C engine with my appraoch, the code is in C++.
I'm using the matlab engine through it's COM interface, without using the mx functions.
I cannot give a working example, check the demo.
Jonathan de Halleux.
|
|
|
|
|
Hi,
I am a beginner in this. I know a little about Matlab and not much about VC++.
I would like to call matlab functions from C.
Can somebody give me the exat syntax of mxCreateCharArray?
I mean like an example with specific values of argument ndim and const int *dims.
#include "matrix.h"
mxArray *mxCreateCharArray(int ndim, const int *dims);
The same for mxCreateDoublematrix,mxCreateString etc...
Thx
F.K
|
|
|
|
|