从MATLAB访问在MEX中创建的稀疏矩阵

时间:2011-05-27 15:00:03

标签: c matlab sparse-matrix mex

我按照here中显示的示例在MEX文件中创建了一个稀疏矩阵。现在我如何从MATLAB整体访问这个矩阵。

#define NZMAX 4
#define ROWS  4
#define COLS  2

int            rows=ROWS, cols=COLS;
mxArray       *ptr_array; /* Pointer to created sparse array. */
static double  static_pr_data[NZMAX] = {5.8, 6.2, 5.9, 6.1};
static int     static_ir_data[NZMAX] = {0, 2, 1, 3};
static int     static_jc_data[COLS+1] = {0, 2, 4};
double        *start_of_pr;
int           *start_of_ir, *start_of_jc;
mxArray       *array_ptr;

/* Create a sparse array. */    
array_ptr = mxCreateSparse(rows, cols, NZMAX, mxREAL); 

/* Place pr data into the newly created sparse array. */ 
start_of_pr = (double *)mxGetPr(array_ptr); 
memcpy(start_of_pr, static_pr_data, NZMAX*sizeof(double));

/* Place ir data into the newly created sparse array. */ 
start_of_ir = (int *)mxGetIr(array_ptr); 
memcpy(start_of_ir, static_ir_data, NZMAX*sizeof(int));

/* Place jc data into the newly created sparse array. */ 
start_of_jc = (int *)mxGetJc(array_ptr); 
memcpy(start_of_jc, static_jc_data, NZMAX*sizeof(int));

/* ... Use the sparse array in some fashion. */
/* When finished with the mxArray, deallocate it. */
mxDestroyArray(array_ptr);

同时在static_pr_dataic_datajc_data中存储值时,是否需要以列主格式存储值?是否可以按行主要格式存储(因为它会加快我的计算速度)?

2 个答案:

答案 0 :(得分:1)

在您链接的示例中,最后一个语句是

mxDestroyArray(array_ptr);

您需要将其作为MEX函数的输出返回,而不是销毁数组。您的MEX函数C / C ++源代码应该有一个名为mexFunction的函数(MEX函数的入口点),如下所示:

void mexFunction(int nlhs, mxArray * plhs[], int nrhs, const mxArray * prhs[])

要从MEX函数返回输出,请将其分配到plhs数组中,如下所示:

plhs[0] = array_ptr; // instead of mxDestroyArray(array_ptr);

将代码编译成MEX函数(我们称之为sparsetest)。像这样从MATLAB调用它:

>> output = sparsetest;

现在output是一个MATLAB变量,包含您在MEX函数中创建的稀疏矩阵。

至于以行主格式存储数据,这是不可能的。 MATLAB只处理列主稀疏矩阵。

答案 1 :(得分:0)

使用engGetVariable()

从matlab结构中获取矩阵字段的提示

我有一个带有字段的结构,它是一个矩阵。在C ++中,相应的结构例如是双**。尝试使用engGetVariable(引擎,MyStruct.theField)访问该字段失败。我使用temp变量来存储MyStruct.theField,然后使用engGetVariable(engine,tempVar),并使用代码从结构中获取矩阵字段

// Fetch struct field using a temp variable
std::string tempName = std::string(field_name) + "_temp";
std::string fetchField = tempName + " = " + std::string(struct_name) 
        + "." + std::string(field_name) + "; ";
matlabExecute(ep, fetchField);
mxArray *matlabArray = engGetVariable(ep, tempName.c_str());

// Get variable elements
const int count = mxGetNumberOfElements(matlabArray);
T *data = (T*) mxGetData(matlabArray);
for (int i = 0; i < count; i++)
    vector[i] = _isnan(data[i]) ? (T) (int) -9999 : (T) data[i];

// Clear temp variable
std::string clearTempVar = "clear " + tempName + "; ";
matlabExecute(ep, clearTempVar);

// Destroy mx object
mxDestroyArray(matlabArray);