void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[]) { /* Check number of input arguments */ if (nrhs > 4) { ERROR("Four or fewer input arguments are required."); } else if (nrhs < 3) { ERROR("At least three input arguments are required."); } /* Check number of output arguments */ if (nlhs > 1) { ERROR("Too many output arguments."); } DOUBLE *X1 = (DOUBLE*) mxGetData(prhs[0]); DOUBLE *X2 = (DOUBLE*) mxGetData(prhs[1]); DOUBLE *S = (DOUBLE*) mxGetData(prhs[2]); INT sqrtFlag; if (nrhs >= 4) { sqrtFlag = (INT)*(DOUBLE*) mxGetData(prhs[3]); if (sqrtFlag > 0) { sqrtFlag = 1; } } else { sqrtFlag = 0; } INT N = (INT) mxGetM(prhs[0]); INT numSamples1 = (INT) mxGetN(prhs[0]); INT numSamples2 = (INT) mxGetN(prhs[1]); if ((numSamples2 != 0) && ((INT) mxGetM(prhs[1]) != N)) { ERROR("The signal dimension (first dimension) of the second sample matrix does not match the signal dimension (first dimension) of the first sample matrix."); } else if (mxGetM(prhs[2]) != N) { ERROR("The first dimension of the Mahalanobis matrix does not match the signal dimension (first dimension) of the first sample matrix."); } else if (mxGetN(prhs[2]) != N) { ERROR("The second dimension of the Mahalanobis matrix does not match the signal dimension (first dimension) of the first sample matrix."); } if (numSamples2 == 0) { X2 = NULL; plhs[0] = mxCreateNumericMatrix(numSamples1, numSamples1, MXPRECISION_CLASS, mxREAL); } else { plhs[0] = mxCreateNumericMatrix(numSamples1, numSamples2, MXPRECISION_CLASS, mxREAL); } DOUBLE *distanceMat = (DOUBLE *) mxGetData(plhs[0]); DOUBLE *tempX1 = (DOUBLE *) MALLOC(N * numSamples1 * sizeof(DOUBLE)); DOUBLE *tempX2 = (DOUBLE *) MALLOC(N * numSamples2 * sizeof(DOUBLE)); DOUBLE *normMat1 = (DOUBLE *) MALLOC(numSamples1 * 1 * sizeof(DOUBLE)); DOUBLE *oneVec = (DOUBLE *) MALLOC(numSamples1 * 1 * sizeof(DOUBLE)); mahalanobis_distance(distanceMat, X1, X2, S, N, numSamples1, numSamples2, \ sqrtFlag, tempX1, tempX2, normMat1, oneVec); FREE(tempX1); FREE(tempX2); FREE(normMat1); FREE(oneVec); }
void pdist_mahalanobis(const double *X, const double *covinv, double *dm, int m, int n) { int i, j; const double *u, *v; double *it = dm; double *dimbuf1, *dimbuf2; dimbuf1 = (double*)malloc(sizeof(double) * 2 * n); dimbuf2 = dimbuf1 + n; for (i = 0; i < m; i++) { for (j = i + 1; j < m; j++, it++) { u = X + (n * i); v = X + (n * j); *it = mahalanobis_distance(u, v, covinv, dimbuf1, dimbuf2, n); } } dimbuf2 = 0; free(dimbuf1); }