How can recursive functions be written in matlab mex ?

Can anyone help me about writing recursive function in matlab mex ? I get error message and then I am told to shutdown and restart matlab. What is the problem ?

3 commentaires

Jan
Jan le 17 Déc 2012
Without seeing the code, it is impossible to guess the bug.
Sujan
Sujan le 18 Déc 2012
Modifié(e) : Jan le 18 Déc 2012
Here is the code. I have managed to avoid the restart problem but recursion doesn't seem to be working.
#include <mex.h>
#include <math.h>
#include <matrix.h>
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
int i, m, n;
double *data1, *data2;
if (nrhs > 1)
mexErrMsgTxt("The number of input arguments must not be greater than 1.");
i = 0;
m = mxGetM(prhs[i]);
n = mxGetN(prhs[i]);
/*create mxarray for the output*/
plhs[i] = mxCreateDoubleMatrix(m, n, mxREAL);
data1 = mxGetPr(prhs[i]);
data2 = (double*)mxMalloc(m*n * sizeof(double));
if (data1[i] == 1){
data2[i] = 1;
}
else{
data2[i] = data1[i]*recurs((data1[i])-1);
}
mxSetPr(plhs[i], data2);
}
[EDITED, Jan, code formatted]
Jan
Jan le 18 Déc 2012
It is better to add all information required to understand the problem by editing the question. If there is a larger number of comments, the inital ones are not visible as default, such that readers will understand the full problem after some interactions only. But the faster a reader can understand the question, the more likely is an answer.

Connectez-vous pour commenter.

Réponses (1)

Jan
Jan le 18 Déc 2012
Modifié(e) : Jan le 18 Déc 2012
mxGetM replies a size_t variable, which is not an int under 64 bit. Better:
mwSize i, m, n;
It is a bad idea to replace the memory of plhs[0] using mxSetPr without clearing the original array. Although this does not crash Matlab immediately, this is prone to leak memory. It would be saver and more efficient to use the already allocated memory of plhs[0]:
data2 = (double *) mxGetPr(plhs[0]);
You did not show the code of "recurs()", so currently there is no recursion at all. Are you sure that you want to reply [1, 0, 0, ...], when the first inpout value is 1?
It is confusing, that you use "i" as index for the input, the output and the first element of the data. It is not wrong, but using a 0 directly would be more clear.
You do not have to inlcude "matrix.h", when "mex.h" is included already.

8 commentaires

The code shown above is the function "recurs.c" itself. So for recursion what I did is I tried to call this function in the following way
data2[i] = data1[i]*recurs((data1[i])-1);
I wrote this to calculate the factorial of number recursively.
The name of this is "recurs.c".
include mex.h
#include math.h
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
int i, m, n;
double *data1, *data2;
if (nrhs > 1)
mexErrMsgTxt("The number of input arguments must not be greater than 1.");
i = 0;
m = mxGetM(prhs[i]);
n = mxGetN(prhs[i]);
/*create mxarray for the output*/
plhs[i] = mxCreateDoubleMatrix(m, n, mxREAL);
data1 = mxGetPr(prhs[i]);
data2 = (double*)mxMalloc(m*n * sizeof(double));
if (data1[0] == 1){
data2[0] = 1;
}
else{
//the following line is for calling the function by itself.
data2[0] = data1[0]*recurs((data1[0])-1);
}
mxSetPr(plhs[0], data2);
} //end of file recurs.c
Could you provide me with solution.
Are you trying to have the recursion take place within the mex function itself? If so, then you need to provide a recurs() function as Jan indicates (a slow and resourse wasting way to do this btw). If you are trying to have the recursion take place at the MATLAB level then you would need to use the mexCallMATLAB API function (an even slower and more resource wasting way to do this btw). Or just write a loop at the C level to calculate the result (faster than both of the above). Which way of recursion are you trying to do ... C level or MATLAB level?
Jan
Jan le 20 Déc 2012
Modifié(e) : Jan le 20 Déc 2012
When the file is called "recurs.c", you call it from Matlab as "recurs()", but this is not possible from inside a C-function. You would need to call "mexFunction()" instead, but this command requires Matlab arrays as input, not a pointer to a double array. Therefore I see a general confusion of Matlab, C and the concept of recursive functions. As James I recommend to re-design the function from the scratch.
Sujan
Sujan le 20 Déc 2012
That was the problem I was facing. I was confused in calling the recursive function of mex by itself. James I have been trying to do the C level. I am trying to calculate factorial to workout the recursion in C level than just use the looping method. I was trying mex recursion to speed up the process than use the matlab recursion for larger matrices.
Jan
Jan le 20 Déc 2012
If this is an exercise only, try it in Matlab at first, because this is less suceptible for errors than C.
@Sujan: Are you simply trying to learn how to do recursion within a mex function, and a factorial was just an example problem to work on to aid the learning process? Or is this entire exercise part of another problem that you are trying to speed up with a mex routine? I am still confused as to what your overall problem and goal is.
Sujan
Sujan le 25 Déc 2012
@ Jan: with Matlab I have no problems.
@ James: I want to learn mex recursion to speed up using mex routine.
Recursion usually does not speed up routines. Sometimes it makes it easier to write routines, but it seldom makes them any faster.
There are some computer languages in which particular forms of recursion ("tail recursion") are optimized, but MATLAB is not one of them.

Connectez-vous pour commenter.

Catégories

En savoir plus sur Write C Functions Callable from MATLAB (MEX Files) dans Centre d'aide et File Exchange

Tags

Question posée :

le 17 Déc 2012

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by