Пример #1
0
void get_P1(const mxArray *model, int *pm, double **P1, double **P1_inf)
{
    int m, i, init;
    
    m       = mxGetM(model);
    if(pm) *pm = m;
    *P1     = mxGetPr(model);
    
    /*** Determine initialization ***/
    for(i=0, init=false; i<m*m; i++) if(mxIsInf((*P1)[i])) { init = true; break; }
    
    if(init) {
        /*** Make a copy first ***/
        double *P1new   = g_P1 = (double *)mxCalloc(m*m, sizeof(double));
        *P1_inf         = g_P1_inf = (double *)mxCalloc(m*m, sizeof(double));
        for(i=0; i<m*m; i++) {
            P1new[i]    = (*P1)[i];
            if(mxIsInf(P1new[i])) {
                P1new[i]        = 0;
                (*P1_inf)[i]    = 1;
            }
            else (*P1_inf)[i]   = 0;
        }
        *P1             = P1new;
    }
    else *P1_inf = (double *)0;
}
Пример #2
0
// Function definitions.
// -----------------------------------------------------------------
int getBoundType (double& lb, double& ub) {
    bool haslb = !mxIsInf(lb);
    bool hasub = !mxIsInf(ub);
    int  btype = haslb + 3*hasub - 2*(haslb && hasub);

    lb = haslb ? lb : 0;
    ub = hasub ? ub : 0;

    return btype;
}
Пример #3
0
double* Options::loadUpperBounds(int n, const mxArray* ptr, double posinfty) {
  double* ub;  // The return value.

  // Load the upper bounds on the variables.
  const mxArray* p = mxGetField(ptr,0,"ub");
  if (p) {

    // Load the upper bounds and check to make sure they are valid.
    int N = Iterate::getMatlabData(p,ub);
    if (N != n)
      throw MatlabException("Upper bounds array must have one element for each optimization variable");

    // Convert MATLAB's convention of infinity to BONMIN's convention
    // of infinity.
    for (int i = 0; i < n; i++)
      if (mxIsInf(ub[i]))
	ub[i] = posinfty;
  } else {

    // If the upper bounds have not been specified, set them to
    // positive infinity.
    ub = new double[n];
    for (int i = 0; i < n; i++)
      ub[i] = posinfty;
  }

  return ub;
}
//Insert Bound Vector
int insertBound(struct sparseblock *blockptr, double *bnd, int nBND, int con_num, int block, int ind, double coeff)
{  
    //Assign Sizes
    blockptr->blocknum = block;
    blockptr->blocksize = nBND;
    blockptr->constraintnum = con_num;
    blockptr->next = NULL;
    blockptr->nextbyblock = NULL;
    //Check we have a finite constraint on this variable
    if(!mxIsInf(bnd[con_num-1])) {
        blockptr->numentries = 1;
        //Allocate LB A Memory (+1s due to Fortran index)
        blockptr->entries   = (double*)malloc((1+1)*sizeof(double));
        if(blockptr->entries == NULL) {
            if(coeff==-1.0)
                sprintf(msgbuf,"Error allocating entries memory for LB[%d, block %d]",con_num, block);
            else
                sprintf(msgbuf,"Error allocating entries memory for UB[%d, block %d]",con_num, block);
            mexErrMsgTxt(msgbuf);
        }
        blockptr->iindices  = (unsigned*)malloc((1+1)*sizeof(unsigned));
        if(blockptr->iindices == NULL) {
            if(coeff==-1.0)
                sprintf(msgbuf,"Error allocating iindices memory for LB[%d, block %d]",con_num, block);
            else
                sprintf(msgbuf,"Error allocating iindices memory for UB[%d, block %d]",con_num, block);
            mexErrMsgTxt(msgbuf);
        }
        blockptr->jindices  = (unsigned*)malloc((1+1)*sizeof(unsigned));
        if(blockptr->jindices == NULL) {
            if(coeff==-1.0)
                sprintf(msgbuf,"Error allocating jindices memory for LB[%d, block %d]",con_num, block);
            else
                sprintf(msgbuf,"Error allocating jindices memory for UB[%d, block %d]",con_num, block);
            mexErrMsgTxt(msgbuf);
        }
        //Fill in entry
        blockptr->entries[1]  = coeff;
        blockptr->iindices[1] = ind;    //don't use con_num incase leading elements are inf (lb = [-Inf,0] .. etc)
        blockptr->jindices[1] = ind;
        #ifdef DEBUG
            if(coeff==-1.0)
                mexPrintf("LB[%d, block %d] i: %d, j: %d, val: %f\n",con_num,block,ind,ind,coeff);
            else
                mexPrintf("UB[%d, block %d] i: %d, j: %d, val: %f\n",con_num,block,ind,ind,coeff);
        #endif
    }
    //Else skip entry
    else {
        blockptr->numentries = 0;
        blockptr->entries  = NULL;
        blockptr->iindices = NULL;
        blockptr->jindices = NULL;
    }
    return blockptr->numentries;
}
Пример #5
0
/*
* egarch_core.c -
* This is a helper function and is part of the UCSD_GARCH toolbox
* You can compile it and should work on any platform.
*
* Author: Kevin Sheppard
* [email protected]
* Revision: 3    Date: 3/1/2005
*/
void egarch_core(double *data, double *parameters, double *back_cast, double *upper, int p, int o, int q, int m, mwSize T, double *ht, double *logHt, double *stdData, double *absStdData)
{
    mwIndex i;
	int j;
	double exp_back_cast, vol, subconst, eLB, hLB;
	
	exp_back_cast=exp(back_cast[0]);
	subconst = 0.797884560802865;
	for (j=0; j<m; j++) 
	{
		/* uses the estimated cov for starting values*/
		logHt[j]=back_cast[0];
		ht[j]=exp_back_cast;
		vol = sqrt(ht[j]);
		stdData[j] = data[j]/vol;
		absStdData[j] = fabs(stdData[j])-subconst;
	}
    eLB = exp_back_cast/10000;
    hLB = back_cast[0] - log(10000);
	for (i=m; i<T; i++) {
		logHt[i]=parameters[0];
		for (j=0; j<p; j++) {
			logHt[i] += parameters[j+1] * absStdData[i-1-j];
		}
		for (j=0; j<o; j++) {
			logHt[i] += parameters[j+p+1] * stdData[i-1-j];
		}
		for (j=0; j<q; j++) {
			logHt[i] += parameters[j+p+o+1] * logHt[i-1-j];
		}
		/* Compute the stanardized residuals*/
		ht[i]=exp(logHt[i]);
		if (ht[i]<eLB)
		{
			ht[i]=eLB;
			logHt[i] = hLB;
		}
		/*Should have a check that not to big*/
		if (ht[i]>upper[0])
		{
			if(mxIsInf(ht[i]))
			{
				ht[i]  = upper[0];
			}
			else
			{
				ht[i]= upper[0] + logHt[i];
			}
			logHt[i] = log(upper[0]);
		}
		vol = sqrt(ht[i]);
		stdData[i] = data[i]/vol;
		absStdData[i] = fabs(stdData[i])-subconst;
 	}
}
Пример #6
0
/*
 *	c o n t a i n s I n f
 */
BooleanType containsInf( const real_t* const data, uint_t dim )
{
	uint_t i;

	if ( data == 0 )
		return BT_FALSE;

	for ( i = 0; i < dim; ++i )
		if ( mxIsInf(data[i]) == 1 )
			return BT_TRUE;

	return BT_FALSE;
}
Пример #7
0
void numeric(double dbl, json_object **jo){

    int intgr = round(dbl);

    if(mxIsNaN(dbl) || mxIsInf(dbl)){
        *jo = NULL;
    }
    else{
        if(fabs(dbl-(double)intgr) > 1e-18){
            *jo = json_object_new_double(dbl);
        }
        else{
            *jo = json_object_new_int(intgr);
        }
    }
}
Пример #8
0
/* Function: mdlOutputs =======================================================
 * Abstract:
 */
static void mdlOutputs(SimStruct *S, int_T tid)
{
    InputRealPtrsType u  = ssGetInputPortRealSignalPtrs(S,0);
    Data              *y = ssGetOutputPortSignal(S,0);

    if (*u[0] > 127 || mxIsInf(*u[0])) {
        y->value = 127;
        y->res = LO_RES;
    } else if (*u[0] < 1.0 && *u[0] > -1.0) {
        y->value = (int8_T) (127.0 * *u[0]);
        y->res   = HI_RES;
    } else {
        y->value = (int8_T) *u[0];
        y->res   = LO_RES;
    }
}
Пример #9
0
void mexFunction(
	int nlhs,	mxArray *plhs[],
	int nrhs, const mxArray *prhs[])
{
	double	*pitch, *wave, pitchRate;
	int fs, pitchLen, waveLen;
	cAudio myAudio;

	/* Check for proper number of arguments */
	if (nrhs!=3){
		char message[200];
		strcpy(message, mexFunctionName());
		strcat(message, " requires 3 input arguments: pitch, pitchRate, fs.");
		mexErrMsgTxt(message);
	}

	/* Dimensions of the input matrix */
	pitchLen = mxGetM(PITCH)*mxGetN(PITCH);
	
	/* Assign pointers to the various parameters */
	pitch = mxGetPr(PITCH);
	pitchRate = mxGetScalar(PITCHRATE);
	fs = (int)mxGetScalar(FS);
	
	/* If some of the elements are nan/inf, change them to 0 */
	double *pitch2=(double *)malloc(pitchLen*sizeof(double));
	memcpy(pitch2, pitch, pitchLen*sizeof(double));
	for (int i=0; i<pitchLen; i++)
		if (mxIsNaN(pitch[i])||mxIsInf(pitch[i]))
			pitch2[i]=0.0;
	
	/* Create a matrix for the return argument */
	waveLen=(int)floor(fs*pitchLen/pitchRate+0.5);
	WAVE = mxCreateDoubleMatrix(waveLen, 1, mxREAL);
	wave = mxGetPr(WAVE);

	myAudio.pitch2wave(pitch2, pitchLen, pitchRate, fs, wave, waveLen);
	free(pitch2);
}
// Function definitions.
// -----------------------------------------------------------------
void mexFunction (int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
    //Input Args
    user_function_data fun;
    double *x0;
    double *ydata;
    double *lb, *ub;

    //Outputs Args
    double *x, *fval, *exitflag, *iter, *feval;

    //Internal Vars
    size_t ndec, ndat, i, j;
    int havJac = 0;
    int printLevel = 0;
    double *bounds = NULL;

    //NL2SOL Vars
    int n;                  //len data
    int p;                  //len x
    int *iv;                //intermediate work array
    double *v;              //intermediate work array
    int liv = 0, lv = 0;    //lengths of intermediate arrays
    int uiparm[2] = {1,0};  //user integer array [citer, printLevel]
    int one = 1, two = 2;
    //Defaults
    int maxfev = 1500;
    int maxiter = 1000;
    double frtol = 1e-7;
    double fatol = 1e-5;
    iterF.enabled = false;

    if (nrhs < 1) {
        if(nlhs < 1)
            printSolverInfo();
        else
            plhs[0] = mxCreateString(NL2SOL_VERSION);

        return;
    }

    //Check user inputs
    checkInputs(prhs,nrhs);

    //Get Sizes
    ndec = mxGetNumberOfElements(pX0);
    ndat = mxGetNumberOfElements(pYDATA);
    //Get Objective Function Handle
    if (mxIsChar(pFUN)) {
        CHECK(mxGetString(pFUN, fun.f, FLEN) == 0,"error reading objective name string");
        fun.nrhs = 1;
        fun.xrhs = 0;
    } else {
        fun.prhs[0] = (mxArray*)pFUN;
        strcpy(fun.f, "feval");
        fun.nrhs = 2;
        fun.xrhs = 1;
    }
    fun.prhs[fun.xrhs] = mxCreateDoubleMatrix(ndec, 1, mxREAL); //x0
    //Check and Get Gradient Function Handle
    if(!mxIsEmpty(pGRAD)) {
        havJac = 1;
        if (mxIsChar(pGRAD)) {
            CHECK(mxGetString(pGRAD, fun.g, FLEN) == 0,"error reading gradient name string");
            fun.nrhs_g = 1;
            fun.xrhs_g = 0;
        } else {
            fun.prhs_g[0] = (mxArray*)pGRAD;
            strcpy(fun.g, "feval");
            fun.nrhs_g = 2;
            fun.xrhs_g = 1;
        }
        fun.prhs_g[fun.xrhs_g] = mxCreateDoubleMatrix(ndec, 1, mxREAL); //x0
    }

    //Get x0 + data
    x0 = mxGetPr(pX0);
    ydata = mxGetPr(pYDATA);

    //Get bounds if specified
    if(nrhs > eUB && !mxIsEmpty(pUB))
    {
        lb = mxGetPr(pLB);
        ub = mxGetPr(pUB);
        bounds = (double*)mxCalloc(2*ndec,sizeof(double));
        //Copy bounds into nlsol b(2,p) array
        for(i=0,j=0; i<2*ndec; i+=2,j++)
        {
            if(mxIsInf(lb[j]))
                bounds[i] = -D1MACH(&two);
            else
                bounds[i] = lb[j];
            if(mxIsInf(ub[j]))
                bounds[i+1] = D1MACH(&two);
            else
                bounds[i+1] = ub[j];
        }
    }

    //Get Options if specified
    if(nrhs > eOPTS) {
        if(mxGetField(pOPTS,0,"display"))
            printLevel = (int)*mxGetPr(mxGetField(pOPTS,0,"display"));
        if(mxGetField(pOPTS,0,"maxfeval"))
            maxfev = (int)*mxGetPr(mxGetField(pOPTS,0,"maxfeval"));
        if(mxGetField(pOPTS,0,"maxiter"))
            maxiter = (int)*mxGetPr(mxGetField(pOPTS,0,"maxiter"));
        if(mxGetField(pOPTS,0,"tolrfun"))
            frtol = *mxGetPr(mxGetField(pOPTS,0,"tolrfun"));
        if(mxGetField(pOPTS,0,"tolafun"))
            fatol = *mxGetPr(mxGetField(pOPTS,0,"tolafun"));
        if(mxGetField(pOPTS,0,"iterfun") && !mxIsEmpty(mxGetField(pOPTS,0,"iterfun")))
        {
            iterF.prhs[0] = (mxArray*)mxGetField(pOPTS,0,"iterfun");
            strcpy(iterF.f, "feval");
            iterF.enabled = true;
            iterF.prhs[1] = mxCreateNumericMatrix(1,1,mxINT32_CLASS,mxREAL);
            iterF.prhs[2] = mxCreateDoubleMatrix(1,1,mxREAL);
            iterF.prhs[3] = mxCreateDoubleMatrix(ndec,1,mxREAL);
        }
    }

    //Create Outputs
    plhs[0] = mxCreateDoubleMatrix(ndec,1, mxREAL);
    plhs[1] = mxCreateDoubleMatrix(1,1, mxREAL);
    plhs[2] = mxCreateDoubleMatrix(1,1, mxREAL);
    plhs[3] = mxCreateDoubleMatrix(1,1, mxREAL);
    plhs[4] = mxCreateDoubleMatrix(1,1, mxREAL);
    x = mxGetPr(plhs[0]);
    fval = mxGetPr(plhs[1]);
    exitflag = mxGetPr(plhs[2]);
    iter = mxGetPr(plhs[3]);
    feval = mxGetPr(plhs[4]);

    //Copy initial guess to x
    memcpy(x,x0,ndec*sizeof(double));

    //Print Header
    if(printLevel) {
        mexPrintf("\n------------------------------------------------------------------\n");
        if(havJac) {
            if(bounds)
                mexPrintf(" This is DN2GB (NL2SOL v%s)\n",NL2SOL_VERSION);
            else
                mexPrintf(" This is DN2G (NL2SOL v%s)\n",NL2SOL_VERSION);
        }
        else {
            if(bounds)
                mexPrintf(" This is DN2FB (NL2SNO v%s)\n",NL2SOL_VERSION);
            else
                mexPrintf(" This is DN2F (NL2SNO v%s)\n",NL2SOL_VERSION);
        }

        mexPrintf(" Authors: John Dennis, David Gay, Roy Welsch\n MEX Interface J. Currie 2012\n\n");
        mexPrintf(" Problem Properties:\n");
        mexPrintf(" # Decision Variables:     %4d\n",ndec);
        mexPrintf(" # Data Points:            %4d\n",ndat);

        mexPrintf("------------------------------------------------------------------\n");
    }

    //Assign Arguments
    n = (int)ndat;
    p = (int)ndec;
    if(bounds)
        liv = 82 + 4*p;
    else
        liv = 82+p;
    if(bounds)
        lv = 105 + p*(n + 2*p + 21) + 2*n;
    else
        lv = 105 + p*(n + 2*p + 17) + 2*n;
    iv = (int*)mxCalloc(liv + 10,sizeof(int));
    v  = (double*)mxCalloc(lv + 10,sizeof(double));
    //Set Options
    //DFAULT(iv,v); //set defaults (OLD v2.2)
    DIVSET(&one,iv,&liv,&lv,v);
    iv[13] = iv[14] = 0;        //no covar
    iv[16] = maxfev;    //limit on fevals + gevals
    iv[17] = maxiter;   //max iter
    iv[18] = 0;     //no iteration printing
    iv[19] = 0;     //no default printing
    iv[20] = 0;     //no output unit printing
    iv[21] = 0;     //no x printing
    iv[22] = 0;     //no summary printing
    iv[23] = 0;     //no initial printing
    v[30] = fatol;
    v[31] = frtol;
    //MEX Options
    uiparm[1] = printLevel;

    //Start timer
    start = clock();

    //Call Algorithm based on Derivatives
    if(havJac)
    {
        //NL2SOL(&n,&p,x,CALCR,CALCJ,iv,v,uiparm,ydata,&fun);
        if(bounds)
            DN2GB(&n,&p,x,bounds,CALCR,CALCJ,iv,&liv,&lv,v,uiparm,ydata,&fun);
        else
            DN2G(&n,&p,x,CALCR,CALCJ,iv,&liv,&lv,v,uiparm,ydata,&fun);
    }
    else
    {
        //#ifdef WIN64
        //    mexErrMsgTxt("Currently NL2SNO crashes when compiled on 64bit systems, try NL2SOL instead (supply a gradient)");
        //#else
        //NL2SNO(&n,&p,x,CALCR,iv,v,uiparm,ydata,&fun);
        if(bounds)
            DN2FB(&n,&p,x,bounds,CALCR,iv,&liv,&lv,v,uiparm,ydata,&fun);
        else
            DN2F(&n,&p,x,CALCR,iv,&liv,&lv,v,uiparm,ydata,&fun);
        //#endif
    }

    //Final Rnorm
    *fval = 2*v[9]; //nl2sol uses 1/2 sum(resid^2)
    //Save Status & Iterations
    *exitflag = getStatus(iv[0]);
    *iter = (double)iv[30];
    *feval = (double)uiparm[0];

    //Print Header
    if(printLevel) {
        //Termination Detected
        switch((int)iv[0])
        {
        //Success
        case 3:
            mexPrintf("\n *** SUCCESSFUL TERMINATION ***\n *** x-convergence ***\n");
            break;
        case 4:
            mexPrintf("\n *** SUCCESSFUL TERMINATION ***\n *** relative function convergence ***\n");
            break;
        case 5:
            mexPrintf("\n *** SUCCESSFUL TERMINATION ***\n *** both x and relative function convergence ***\n");
            break;
        case 6:
            mexPrintf("\n *** SUCCESSFUL TERMINATION ***\n *** absolute function convergence ***\n");
            break;
        //Error
        case 9:
            mexPrintf("\n *** MAXIMUM FUNCTION EVALUATIONS REACHED ***\n");
            break;
        case 10:
            mexPrintf("\n *** MAXIMUM ITERATIONS REACHED ***\n");
            break;
        case 13:
            mexPrintf("\n *** ERROR: f(x) cannot be computed at the initial x ***\n");
            break;
        case 14:
            mexPrintf("\n *** ERROR: bad parameters passed to asses ***\n");
            break;
        case 15:
            mexPrintf("\n *** ERROR: the jacobian cannot be computed at x ***\n");
            break;
        case 16:
            mexPrintf("\n *** ERROR: internal parameter n or p out of range ***\n");
            break;
        case 17:
            mexPrintf("\n *** ERROR: restart attempted with n or p changed ***\n");
            break;
        case 50:
            mexPrintf("\n *** ERROR: internal parameter iv(1) is out of range ***\n");
            break;
        //Early Exit
        case 7:
            mexPrintf("\n *** TERMINATION: EARLY EXIT ***\n *** CAUSE: singular convergence. the hessian near the current iterate appears to be singular or nearly so. ***\n");
            break;
        case 8:
            mexPrintf("\n *** TERMINATION: EARLY EXIT ***\n *** CAUSE: false convergence. the iterates appear to be converging to a noncritical point. this may mean that the convergence tolerances are too small ***\n");
            break;
        case 11:
            mexPrintf("\n *** TERMINATION: USER EXITED ***\n");
            break;
        //Other Error
        default:
            mexPrintf("\n *** ERROR: internal error code %d ***\n",(int)iv[0]);
            break;
        }

        if(*exitflag==1)
            mexPrintf("\n Final SSE: %12.5g\n In %3.0f iterations\n",*fval,*iter);

        mexPrintf("------------------------------------------------------------------\n\n");
    }

    //Free Memory
    if(iv) mxFree(iv);
    iv = NULL;
    if(v) mxFree(v);
    v = NULL;
    if(bounds) mxFree(bounds);
    bounds = NULL;
}
//CALCR
static void CALCR(int *n, int *p, double *x, int *nf, double *r, int *uiparm, double *ydata, void *ufparm)
{
    bool havrnorm = false, stop = false;
    int i, stat;
    double *fval, rnorm = 0;
    clock_t end;
    double evaltime;

    //Get User Data
    user_function_data *fun = (user_function_data*)ufparm;

    fun->plhs[0] = NULL;
    memcpy(mxGetPr(fun->prhs[fun->xrhs]), x, *p * sizeof(double));

    stat = mexCallMATLAB(1, fun->plhs, fun->nrhs, fun->prhs, fun->f);
    if(stat)
        mexErrMsgTxt("Error calling Objective Function!");

    //Get Objective
    fval = mxGetPr(fun->plhs[0]);

    //Assign Objective + subtract ydata
    for(i=0; i<*n; i++) {
        r[i] = fval[i]-ydata[i];

        //Check for out of bounds, will try a smaller step size
        if(mxIsInf(r[i]) || mxIsNaN(r[i]))
            *nf = 0;
    }

    // Clean up Ptr
    mxDestroyArray(fun->plhs[0]);

    //Iteration Printing
    if(uiparm[1] > 1) {
        //Get Execution Time
        end = clock();
        evaltime = ((double)(end-start))/CLOCKS_PER_SEC;

        //Calculate Residual Norm
        rnorm = 0;
        havrnorm = true;
        for(i=0; i<*n; i++)
            rnorm += r[i]*r[i];

        if(uiparm[0] == 1 || !(uiparm[0]%10))
            mexPrintf(" feval       time            sse\n");

        mexPrintf("%5d       %5.2f     %12.5g\n",uiparm[0],evaltime,rnorm);
        mexEvalString("drawnow;"); //flush draw buffer
    }

    //Iteration Callback
    if(iterF.enabled)
    {
        //Calculate sse if we don't have it
        if(!havrnorm)
            for(i=0; i<*n; i++)
                rnorm += r[i]*r[i];;

        iterF.plhs[0] = NULL;
        memcpy(mxGetData(iterF.prhs[1]), uiparm, sizeof(int));
        memcpy(mxGetPr(iterF.prhs[2]), &rnorm, sizeof(double));
        memcpy(mxGetPr(iterF.prhs[3]), x, *p * sizeof(double));
        stat = mexCallMATLAB(1, iterF.plhs, 4, iterF.prhs, iterF.f);
        if(stat)
            mexErrMsgTxt("Error calling Callback Function!");

        //Collect return argument
        stop = *(bool*)mxGetData(iterF.plhs[0]);
        // Clean up Ptr
        mxDestroyArray(iterF.plhs[0]);

        //Warn user stop not implemented
        if(stop)
            mexWarnMsgTxt("NL2SOL does not implement the stop feature of iterfun");
    }

    uiparm[0]++;
}
Пример #12
0
//Gateway routine
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
	//Read input arguments
	char outputFormat[10];
	char outputVarName[MAXVARNAMESIZE];
	int	outputVarSampsPerChan;
	double timeout;
	int numSampsPerChan;
	bool outputData; //Indicates whether to return an outputData argument
	mxClassID outputDataClass;
	uInt32 bufSize;
	bool writeDigitalLines;
	uInt32 bytesPerChan=0;
	TaskHandle taskID, *taskIDPtr;
	int32 status;

	//Get TaskHandle
	taskIDPtr = (TaskHandle*)mxGetData(mxGetProperty(prhs[0],0, "taskID"));
	taskID = *taskIDPtr;

	//Determine if this is a buffered read operation
	status = DAQmxGetBufInputBufSize(taskID, &bufSize);
	if (status)
		handleDAQmxError(status, "DAQmxGetBufInputBufSize");

	//Handle input arguments
	if ((nrhs < 2) || mxIsEmpty(prhs[1]) || mxIsInf(mxGetScalar(prhs[1])))
	{
		if (bufSize==0)
			numSampsPerChan = 1;
		else
			numSampsPerChan = DAQmx_Val_Auto;
	}
	else
		numSampsPerChan = (int) mxGetScalar(prhs[1]);
	
	if ((nrhs < 3) || mxIsEmpty(prhs[2]))
	{
		//Automatic determination of read type
		bool isLineBased = (bool) mxGetScalar(mxGetProperty(prhs[0],0,"isLineBasedDigital"));		

		if ((bufSize==0) && isLineBased) //This is a non-buffered, line-based Task: return data as a double array
			outputDataClass = mxDOUBLE_CLASS;
		else
		{
			status = DAQmxGetReadDigitalLinesBytesPerChan(taskID,&bytesPerChan); //This actually returns the number of bytes required to represent one sample of Channel data
			if (status)
				handleDAQmxError(status, "DAQmxGetReadDigitalLinesBytesPerChan");

			if (bytesPerChan <= 8)
				outputDataClass = mxUINT8_CLASS;
			else if (bytesPerChan <= 16)
				outputDataClass = mxUINT16_CLASS;
			else if (bytesPerChan <= 32)
				outputDataClass = mxUINT32_CLASS;
			else
				mexErrMsgTxt("It is not currently possible to read integer values from Task with greater than 32 lines per sample value");
		}
	}
	else
	{
		mxGetString(prhs[2], outputFormat, 10);		

		if (_strcmpi(outputFormat,"uint8"))
			outputDataClass = mxUINT8_CLASS;
		else if (_strcmpi(outputFormat,"uint16"))
			outputDataClass = mxUINT16_CLASS;
		else if (_strcmpi(outputFormat,"uint32"))
			outputDataClass = mxUINT32_CLASS;
		else if (_strcmpi(outputFormat,"double"))
			outputDataClass = mxDOUBLE_CLASS;
		else if (_strcmpi(outputFormat,"logical"))
			outputDataClass = mxLOGICAL_CLASS;
		else
			mexErrMsgTxt("The specified 'outputFormat' value (case-sensitive) is not recognized.");
	}

	if ((outputDataClass == mxDOUBLE_CLASS) || (outputDataClass == mxLOGICAL_CLASS))
	{
		writeDigitalLines = true;
		if (bytesPerChan == 0)
		{
			status = DAQmxGetReadDigitalLinesBytesPerChan(taskID,&bytesPerChan); //This actually returns the number of bytes required to represent one sample of Channel data
			if (status)
				handleDAQmxError(status, "DAQmxGetReadDigitalLinesBytesPerChan");
		}			
	}
	else
		writeDigitalLines = false;


	if ((nrhs < 4) || mxIsEmpty(prhs[3]) || mxIsInf(mxGetScalar(prhs[3])))
		timeout = DAQmx_Val_WaitInfinitely;
	else
		timeout = mxGetScalar(prhs[3]);


	if ((nrhs < 5) || mxIsEmpty(prhs[4])) //OutputVarSizeOrName argument
	{
		outputData = true;
		outputVarSampsPerChan = numSampsPerChan; //If value is DAQmx_Val_Auto, then the # of samples available will be queried before allocting array
	}
	else
	{
		outputData = mxIsNumeric(prhs[4]);
		if (outputData)
		{
			if (nlhs < 2)
				mexErrMsgTxt("There must be two output arguments specified if a preallocated MATLAB variable is not specified");
			outputVarSampsPerChan = (int) mxGetScalar(prhs[4]);
		}
		else
			mxGetString(prhs[4], outputVarName, MAXVARNAMESIZE);
	}

	//Determin # of output channels
	uInt32 numChannels; 
	DAQmxGetReadNumChans(taskID, &numChannels); //Reflects number of channels in Task, or the number of channels specified by 'ReadChannelsToRead' property
	
	//Determine output buffer/size (creating if needed)
	mxArray *outputDataBuf, *outputDataBufTrue;
	void *outputDataPtr;

	//float64 *outputDataPtr;
	if (outputData)
	{
		mwSize numRows;

		if (outputVarSampsPerChan == DAQmx_Val_Auto)
		{
			status = DAQmxGetReadAvailSampPerChan(taskID, (uInt32 *)&outputVarSampsPerChan);
			if (status)
			{
				handleDAQmxError(status, "DAQmxGetReadAvailSampPerChan");
				return;
			}
		}
		
		if (writeDigitalLines)
			numRows = (mwSize) (outputVarSampsPerChan * bytesPerChan);
		else
			numRows = (mwSize) outputVarSampsPerChan;
		
		if (outputDataClass == mxDOUBLE_CLASS)
		{
			outputDataBuf = mxCreateNumericMatrix(numRows,numChannels,mxUINT8_CLASS,mxREAL);
			outputDataBufTrue = mxCreateDoubleMatrix(numRows,numChannels,mxREAL);
		}
		else
			outputDataBuf = mxCreateNumericMatrix(numRows,numChannels,outputDataClass,mxREAL);
	}
	else //I don't believe this is working
	{
		outputDataBuf = mexGetVariable("caller", outputVarName);
		outputVarSampsPerChan = mxGetM(outputDataBuf);
		//TODO: Add check to ensure WS variable is of correct class
	}

	outputDataPtr = mxGetData(outputDataBuf);

	//Read data
	int32 numSampsRead;
	int32 numBytesPerSamp;

	switch (outputDataClass)
	{
	case mxUINT8_CLASS:
		status = DAQmxReadDigitalU8(taskID, numSampsPerChan, timeout, fillMode, (uInt8*) outputDataPtr, outputVarSampsPerChan * numChannels, &numSampsRead, NULL);
		break;
	case mxUINT16_CLASS:
		status = DAQmxReadDigitalU16(taskID, numSampsPerChan, timeout, fillMode, (uInt16*) outputDataPtr, outputVarSampsPerChan * numChannels, &numSampsRead, NULL);
		break;
	case mxUINT32_CLASS:
		status = DAQmxReadDigitalU32(taskID, numSampsPerChan, timeout, fillMode, (uInt32*) outputDataPtr, outputVarSampsPerChan * numChannels, &numSampsRead, NULL);
		break;
	case mxLOGICAL_CLASS:
	case mxDOUBLE_CLASS:
		status = DAQmxReadDigitalLines(taskID, numSampsPerChan, timeout, fillMode, (uInt8*) outputDataPtr, outputVarSampsPerChan * numChannels * bytesPerChan, &numSampsRead, &numBytesPerSamp, NULL);
		break;
	default:
		mexErrMsgTxt("There must be two output arguments specified if a preallocated MATLAB variable is not specified");

	}

	//Return output data
	if (!status)
	{
		//mexPrintf("Successfully read %d samples of data\n", numSampsRead);		

		if (outputData)
		{
			if (nlhs > 0)
			{
				if (outputDataClass == mxDOUBLE_CLASS)
				{
					//Convert logical data to double type
					double *outputDataTruePtr = mxGetPr(outputDataBufTrue);
					for (size_t i=0;i < mxGetNumberOfElements(outputDataBuf);i++)	
						*(outputDataTruePtr+i) = (double) *((uInt8 *)outputDataPtr+i);
						
					mxDestroyArray(outputDataBuf);

					plhs[0] = outputDataBufTrue;
				}
				else
					plhs[0] = outputDataBuf;
			}
			else
				mxDestroyArray(outputDataBuf); //If you don't read out, all the reading was done for naught
		}
		else //I don't believe this is working
		{
			mexErrMsgTxt("invalid branch");
			mexPutVariable("caller", outputVarName, outputDataBuf);
			
			if (nlhs > 0) //Return empty value for output data
				plhs[0] = mxCreateDoubleMatrix(0,0,mxREAL);
		}			

		if (nlhs > 1) //Return number of samples actually read
		{
			double *sampsReadOutput;

			plhs[1] = mxCreateDoubleScalar(0);	
			sampsReadOutput = mxGetPr(plhs[1]);

			*sampsReadOutput = (double)numSampsRead;
		}
	}
	else //Read failed
		handleDAQmxError(status, mexFunctionName());

}
//Gateway routine
//sampsPerChanWritten = writeAnalogData(task, writeData, timeout, autoStart, numSampsPerChan)
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
	//General vars
	char errMsg[512];
	
	//Read input arguments
	float64 timeout;
	int numSampsPerChan;
	bool32 autoStart;
	TaskHandle taskID, *taskIDPtr;

	//Get TaskHandle
	taskIDPtr = (TaskHandle*)mxGetData(mxGetProperty(prhs[0],0, "taskID"));
	taskID = *taskIDPtr;

	if ((nrhs < 3) || mxIsEmpty(prhs[2]))
		timeout = 10.0;
	else
	{
		timeout = (float64) mxGetScalar(prhs[2]);
		if (mxIsInf(timeout))
			timeout = DAQmx_Val_WaitInfinitely;
	}

	if ((nrhs < 4) || mxIsEmpty(prhs[3])) {
		int32 sampTimingType = 0;
		int32 status = DAQmxGetSampTimingType(taskID,&sampTimingType);
		if (status!=0) {
			mexErrMsgTxt("Failed to get sample timing type from DAQmx.");
		}
		autoStart = (sampTimingType==DAQmx_Val_OnDemand);
	}
	else
		autoStart = (bool32) mxGetScalar(prhs[3]);

	size_t numRows = mxGetM(prhs[1]);
	if ((nrhs < 5) || mxIsEmpty(prhs[4]))
		numSampsPerChan = numRows;
	else
		numSampsPerChan = (int) mxGetScalar(prhs[4]);

	//Verify correct input length

	//Write data
	int32 sampsWritten;
	int32 status;


	switch (mxGetClassID(prhs[1]))
	{	
		case mxUINT16_CLASS:
			status = DAQmxWriteBinaryU16(taskID, numSampsPerChan, autoStart, timeout, dataLayout, (uInt16*) mxGetData(prhs[1]), &sampsWritten, NULL);
		break;

		case mxINT16_CLASS:
			status = DAQmxWriteBinaryI16(taskID, numSampsPerChan, autoStart, timeout, dataLayout, (int16*) mxGetData(prhs[1]), &sampsWritten, NULL);
		break;

		case mxDOUBLE_CLASS:
			status = DAQmxWriteAnalogF64(taskID, numSampsPerChan, autoStart, timeout, dataLayout, (float64*) mxGetData(prhs[1]), &sampsWritten, NULL);
		break;

		default:
			sprintf_s(errMsg,"Class of supplied writeData argument (%s) is not valid", mxGetClassName(prhs[1]));
			mexErrMsgTxt(errMsg);
	}

	//Handle output arguments and errors
	if (!status)
	{
		if (nlhs > 0) {
			plhs[0] = mxCreateDoubleScalar(0);	
			double *sampsPerChanWritten = mxGetPr(plhs[0]);
		}

		//mexPrintf("Successfully wrote %d samples of data\n", sampsWritten);		
	}
	else //Write failed
		handleDAQmxError(status, mexFunctionName());
}
Пример #14
0
/* -------------------------------------------------------------
  The gateway routine.
------------------------------------------------------------- */
void mexFunction( int nlhs, mxArray *plhs[],
                  int nrhs, const mxArray *prhs[] )
{
  int exitflag;      /* status of the solution (output arg) */
  long t;            /* number of iterations (output arg) */
  double *x;         /* solution vector (output arg)*/
  double *History;   /* UB and LB history (output arg) */
  int verb;          /* verbosity (input arg)*/
  long tmax;         /* max number of iteration (input arg)*/
  double tolrel;     /* stopping condition (input arg) */
  double tolabs;     /* stopping condition (input arg) */
  double *x0;        /* initial solution (input arg)*/
  double *f;         /* vector f (input arg) */
  double b;          /* scalar b (input arg) */
  uint16_T *I;       /* vector of uint16_T (input arg) */
  double *diag_H;    /* diagonal of matrix H */
  long i ;           /* loop variable */
  double *tmp_ptr;

  /*------------------------------------------------------------------- */
  /* Take input arguments                                               */
  /*         [...] = qpssvm_mex(H,f,b,I,x0,tmax,tolabs,tolrel,verb)     */
  /*------------------------------------------------------------------- */

  if( nrhs != 9) mexErrMsgTxt("Incorrect number of input arguments.");

  /* matrix H */
  matrix_H = mxGetPr(prhs[0]);
  dim = mxGetM(prhs[0]);
  if(dim != mxGetN(prhs[0])) mexErrMsgTxt("Matrix H mast be squared.");

  /* vector f */
  f = mxGetPr(prhs[1]);
  if((MAX(mxGetM(prhs[1]),mxGetN(prhs[1])) != dim) ||
     (MIN(mxGetM(prhs[1]),mxGetN(prhs[1])) != 1))
      mexErrMsgTxt("Vector f is of wrong size.");

  /* vector b */
  b = mxGetScalar(prhs[2]);

  /* vector I */
  I = (uint16_T*)mxGetPr(prhs[3]);
  if((MAX(mxGetM(prhs[3]),mxGetN(prhs[3])) != dim) ||
     (MIN(mxGetM(prhs[3]),mxGetN(prhs[3])) != 1))
      mexErrMsgTxt("Vector I is of wrong size.");

  /* vector x0 */
  x0 = mxGetPr(prhs[4]);
  if((MAX(mxGetM(prhs[4]),mxGetN(prhs[4])) != dim) ||
     (MIN(mxGetM(prhs[4]),mxGetN(prhs[4])) != 1))
      mexErrMsgTxt("Vector x0 is of wrong size.");

  /* maximal allowed number of iterations */
  tmax = mxIsInf( mxGetScalar(prhs[5])) ? INT_MAX : (long)mxGetScalar(prhs[5]);

  /* abs. precision defining stopping cond*/
  tolabs = mxGetScalar(prhs[6]);

  /* rel. precision defining stopping cond*/
  tolrel = mxGetScalar(prhs[7]);

  /* verbosity parameter */
  verb = (int)mxGetScalar(prhs[8]);  /* verbosity on/off */

  /* print input setting if required */
  if( verb > 0 ) {
    mexPrintf("Settings of QP solver:\n");
    mexPrintf("tmax   : %d\n", tmax );
    mexPrintf("tolabs : %f\n", tolabs );
    mexPrintf("tolrel : %f\n", tolrel );
    mexPrintf("dim    : %d\n", dim );
    mexPrintf("b      : %f\n", b );
    mexPrintf("verb   : %d\n", verb );
  }

  /*-------------------------------------------------------------------
     Inicialization
   ------------------------------------------------------------------- */

  /* solution vector x [dim x 1] */
  plhs[0] = mxCreateDoubleMatrix(dim,1,mxREAL);
  x = mxGetPr(plhs[0]);
  for(i=0; i < dim; i++ ) {
     x[i] = x0[i];
  }

  /* make diagonal of the Hessian matrix */
  diag_H = mxCalloc(dim, sizeof(double));
  if( diag_H == NULL ) mexErrMsgTxt("Not enough memory.");
  /* to replace with memcpy(void *dest, const void *src, size_t n); */
  for(i = 0; i < dim; i++ ) {
    diag_H[i] = matrix_H[dim*i+i];
  }

  /* counter of access to matrix H */
  access = dim;

  /*-------------------------------------------------------------------
   Call the QP solver.
   -------------------------------------------------------------------*/
/* exitflag = qpssvm_solver( &get_col, diag_H, f, b, I, x, dim, tmax,
      tolabs, tolrel, &t, &History, verb );
 */

  exitflag = qpssvm_imdm( &get_col, diag_H, f, b, I, x, dim, tmax,
         tolabs, tolrel, &t, &History, verb );


  /*-------------------------------------------------------------------
    Set up output arguments
         [x,exitflag,t,access,History] = qpssvm_mex(...)
  ------------------------------------------------------------------- */

  /* exitflag [1x1] */
  plhs[1] = mxCreateDoubleMatrix(1,1,mxREAL);
  *(mxGetPr(plhs[1])) = (double)exitflag;

  /* t [1x1] */
  plhs[2] = mxCreateDoubleMatrix(1,1,mxREAL);
  *(mxGetPr(plhs[2])) = (double)t;

  /* access [1x1] */
  plhs[3] = mxCreateDoubleMatrix(1,1,mxREAL);
  *(mxGetPr(plhs[3])) = (double)access;

  /* History [2 x (t+1)] */
  plhs[4] = mxCreateDoubleMatrix(2,t+1,mxREAL);
  tmp_ptr = mxGetPr( plhs[4] );
  for( i = 0; i <= t; i++ ) {
     tmp_ptr[INDEX(0,i,2)] = History[INDEX(0,i,2)];
     tmp_ptr[INDEX(1,i,2)] = History[INDEX(1,i,2)];
  }

  /*-------------------------------------------------------------------
     Free used memory
  ------------------------------------------------------------------- */
  mxFree( History );
  mxFree( diag_H );

  return;
}
Пример #15
0
/* -------------------------------------------------------------------
 Main MEX function - interface to Matlab.

  [vec_x,exitflag,t,access,Nabla] = 
         gsmo_mex(H,f,a,b,LB,UB,x0,Nabla0,tmax,tolKKT,verb);

-------------------------------------------------------------------- */
void mexFunction( int nlhs, mxArray *plhs[],int nrhs, const mxArray*prhs[] )
{
  int verb;          
  uint32_t i;         
  uint32_t MaxIter;   
  double TolKKT; 
  double *vec_x;         /* output arg -- solution*/ 
  double *vec_x0;         
  double *diag_H;    /* diagonal of matrix H */
  double *f;         /* vector f */
  double *a;
  double b;
  double *LB;
  double *UB;
  double fval;
  
  /*------------------------------------------------------------------- */
  /* Take input arguments                                               */
  /*------------------------------------------------------------------- */

  if( nrhs != 10) mexErrMsgTxt("Incorrect number of input arguments.");

  mat_H = mxGetPr(prhs[0]);
  nVar = mxGetM(prhs[0]);
  f = mxGetPr(prhs[1]);   
  a = mxGetPr(prhs[2]);
  b = mxGetScalar(prhs[3]);
  LB = mxGetPr(prhs[4]);
  UB = mxGetPr(prhs[5]);
  vec_x0 = mxGetPr(prhs[6]);
  MaxIter = mxIsInf( mxGetScalar(prhs[7])) ? INT_MAX : (long)mxGetScalar(prhs[7]);
  TolKKT = mxGetScalar(prhs[8]); 
  verb = (int)(mxGetScalar(prhs[9])); 
    
  if( verb > 0 ) {
    mexPrintf("Settings of QP solver\n");
    mexPrintf("MaxIter : %d\n", MaxIter );
    mexPrintf("TolKKT  : %f\n", TolKKT );
    mexPrintf("nVar    : %d\n", nVar );
    mexPrintf("verb    : %d\n", verb );
  }

  plhs[0] = mxCreateDoubleMatrix(nVar,1,mxREAL);
  vec_x = mxGetPr(plhs[0]);
  memcpy( vec_x, vec_x0, sizeof(double)*nVar );

  diag_H = mxCalloc(nVar, sizeof(double));
  if( diag_H == NULL ) mexErrMsgTxt("Not enough memory.");
  for(i = 0; i < nVar; i++ ) 
    diag_H[i] = mat_H[nVar*i+i];
  

  /*------------------------------------------------------------------- */
  /* Call QP solver                                                     */
  /*------------------------------------------------------------------- */
  state = libqp_gsmo_solver( &get_col, diag_H, f, a, b, LB, UB, vec_x, 
                        nVar, MaxIter, TolKKT, NULL );

  /*------------------------------------------------------------------- */
  /* Generate outputs                                                   */
  /*------------------------------------------------------------------- */

  plhs[1] = mxCreateDoubleScalar(state.QP);
  plhs[2] = mxCreateDoubleScalar((double)state.exitflag);
  plhs[3] = mxCreateDoubleScalar((double)state.nIter);


  /*------------------------------------------------------------------- */
  /* Clean up                                                           */
  /*------------------------------------------------------------------- */
  mxFree( diag_H );
}
Пример #16
0
/* -------------------------------------------------------------
  MEX main function.
------------------------------------------------------------- */
void mexFunction( int nlhs, mxArray *plhs[],
                  int nrhs, const mxArray *prhs[] )
{
  int verb;          
  uint32_t MaxIter;
  uint32_t *vec_I; 
  uint32_t nConstr; 
  uint8_t *vec_S;
  double *vec_x;         
  double TolRel;     
  double TolAbs;     
  double QP_TH;
  double *vec_x0;        
  double *vec_f;         
  double *vec_b;
  double *diag_H;    
  long i ;           
  libqp_state_T state;
  double *tmp;

  /*------------------------------------------------------------------- 
     Get input arguments
   ------------------------------------------------------------------- */
  if( nrhs != 12) mexErrMsgTxt("Incorrect number of input arguments.");
  
  mat_H = (mxArray*)prhs[0];
  nVar = mxGetM(prhs[0]);

  diag_H = mxGetPr(prhs[1]);

  vec_f = mxGetPr(prhs[2]);
  vec_b = (double*)mxGetPr(prhs[3]);
  vec_I = (uint32_t*)mxGetPr(prhs[4]);
  vec_S = (uint8_t*)mxGetPr(prhs[5]);

  nConstr = LIBQP_MAX(mxGetN(prhs[3]),mxGetM(prhs[3]));

  vec_x0 = mxGetPr(prhs[6]);
  MaxIter = mxIsInf( mxGetScalar(prhs[7])) ? 0xFFFFFFFF : (uint32_t)mxGetScalar(prhs[7]);
  TolAbs = mxGetScalar(prhs[8]);   
  TolRel = mxGetScalar(prhs[9]);   
  QP_TH = mxGetScalar(prhs[10]);   
  verb = (int)mxGetScalar(prhs[11]);  

  /* print input setting if required */  
  if( verb > 0 ) {
    mexPrintf("Settings of LIBQP_SSVM solver:\n");
    mexPrintf("MaxIter  : %u\n", MaxIter );
    mexPrintf("TolAbs   : %f\n", TolAbs );
    mexPrintf("TolRel   : %f\n", TolRel );
    mexPrintf("QP_TH    : %f\n", QP_TH );
    mexPrintf("nVar     : %u\n", nVar );
    mexPrintf("nConstr  : %u\n", nConstr );
  }     
  
  /*------------------------------------------------------------------- 
     Inicialization                                                     
   ------------------------------------------------------------------- */

  /* create solution vector x [nVar x 1] */
  plhs[0] = mxCreateDoubleMatrix(nVar,1,mxREAL);
  vec_x = mxGetPr(plhs[0]);
  memcpy( vec_x, vec_x0, sizeof(double)*nVar );
  
  /*------------------------------------------------------------------- 
   Call the QP solver.
   -------------------------------------------------------------------*/

  if( mxIsSparse(mat_H)== true )
  {
    col_buf0 = mxCalloc(nVar,sizeof(double));
    if( col_buf0 == NULL)
      mexErrMsgTxt("Cannot allocate memory for col_buf0.");      

    col_buf1 = mxCalloc(nVar,sizeof(double));
    if( col_buf1 == NULL)
      mexErrMsgTxt("Cannot allocate memory for col_buf1.");      

    /*    tmp = get_col_sparse(nVar-1);
    for(i=0; i<nVar; i++)
    {
    mexPrintf("%d: %f\n",i,tmp[i]);
      vec_x[i] = tmp[i];
    }
*/
    
    state = libqp_splx_solver(&get_col_sparse, diag_H, vec_f, vec_b, vec_I, vec_S, vec_x, nVar, 
           MaxIter, TolAbs, TolRel, QP_TH, NULL);

    mxFree(col_buf0);
    mxFree(col_buf1);
    
  }
  else
  {

    /*    tmp = get_col(nVar-1);
    for(i=0; i<nVar; i++)
    {
       mexPrintf("%d: %f\n",i,tmp[i]);
      vec_x[i] = tmp[i];
    }
    */
   
    state = libqp_splx_solver(&get_col, diag_H, vec_f, vec_b, vec_I, vec_S, vec_x, nVar, 
                              MaxIter, TolAbs, TolRel, QP_TH, NULL);
   
  }
  
  /*------------------------------------------------------------------- 
    Set output arguments                                                   
    [x,QP,QD,exitflag,nIter] = libqp_splx_mex(...)
  ------------------------------------------------------------------- */

  plhs[1] = mxCreateDoubleMatrix(1,1,mxREAL);
  *(mxGetPr(plhs[1])) = (double)state.QP;

  plhs[2] = mxCreateDoubleMatrix(1,1,mxREAL);
  *(mxGetPr(plhs[2])) = (double)state.QD;

  plhs[3] = mxCreateDoubleMatrix(1,1,mxREAL);
  *(mxGetPr(plhs[3])) = (double)state.exitflag;

  plhs[4] = mxCreateDoubleMatrix(1,1,mxREAL);
  *(mxGetPr(plhs[4])) = (double)state.nIter;

  
  return; 
}
Пример #17
0
int Options::loadConstraintBounds (const mxArray* ptr, double*& cl, 
				   double*& cu, double neginfty,
				   double posinfty, int &lin, int &nlin) {
  int m = 0;  // The return value is the number of constraints.
  int tm;
  //Defaults
  lin = 0; nlin = 0;

  // LOAD CONSTRAINT BOUNDS.
  // If the user has specified constraints bounds, then she must
  // specify *both* the lower and upper bounds.
  const mxArray* pl = mxGetField(ptr,0,"cl");
  const mxArray* pu = mxGetField(ptr,0,"cu");
  const mxArray* prl = mxGetField(ptr,0,"rl"); //linear constraint bounds
  const mxArray* pru = mxGetField(ptr,0,"ru");
  if (pl || pu || prl || pru) {

    // Check to make sure the constraint bounds are valid.
    if ((!pl ^ !pu) || (!prl ^ !pru))
      throw MatlabException("You must specify both lower and upper bounds on the constraints");
    if (pl && (!mxIsDouble(pl) || !mxIsDouble(pu) || (mxGetNumberOfElements(pl) != mxGetNumberOfElements(pu))))
      throw MatlabException("The nonlinear constraints lower and upper bounds must both be double-precision arrays with the same number of elements");
    if (prl && (!mxIsDouble(prl) || !mxIsDouble(pru) || (mxGetNumberOfElements(prl) != mxGetNumberOfElements(pru))))
      throw MatlabException("The linear constraints lower and upper bounds must both be double-precision arrays with the same number of elements");
    // Get the number of constraints.
    if(pl && prl) {
        lin = (int)mxGetNumberOfElements(prl);
        nlin = (int)mxGetNumberOfElements(pl);
        m = lin+nlin;
    }
    else if(pl) {
        lin = 0;
        nlin = (int)mxGetNumberOfElements(pl);
        m = nlin;        
    }
    else {
        lin = (int)mxGetNumberOfElements(prl);
        nlin = 0;
        m = lin;
    }

    // Load the lower bounds on the constraints and convert MATLAB's
    // convention of infinity to IPOPT's convention of infinity.
    cl = new double[m];
    cu = new double[m];
    if(pl && prl) {
        tm = (int)mxGetNumberOfElements(pl);
        copymemory(mxGetPr(pl),cl,tm);
        copymemory(mxGetPr(pu),cu,tm);
        copymemory(mxGetPr(prl),&cl[tm],(int)mxGetNumberOfElements(prl));
        copymemory(mxGetPr(pru),&cu[tm],(int)mxGetNumberOfElements(pru));
    }
    else if(pl) {
        copymemory(mxGetPr(pl),cl,m);
        copymemory(mxGetPr(pu),cu,m);
    }
    else {
        copymemory(mxGetPr(prl),cl,m);
        copymemory(mxGetPr(pru),cu,m);
    }

    // Convert MATLAB's convention of infinity to IPOPT's convention
    // of infinity.
    for (int i = 0; i < m; i++) {
      if (mxIsInf(cl[i])) cl[i] = neginfty;
      if (mxIsInf(cu[i])) cu[i] = posinfty;
    }
  }

  return m;
}
Пример #18
0
int get_IntgrOptions(const mxArray *options, cvmPbData thisPb, booleantype fwd, int lmm,
                     int *maxord, booleantype *sld, booleantype *errmsg,
                     long int *mxsteps,
                     int *itol, realtype *reltol, double *Sabstol, double **Vabstol,
                     double *hin, double *hmax, double *hmin, double *tstop,
                     booleantype *rhs_s)
{
  mxArray *opt;
  int q;
  long int i, m, n;
  double *tmp;
  char *fctName;
  char *fwd_fctName = "CVodeInit/CVodeReInit";
  char *bck_fctName = "CVodeInitB/CVodeReInitB";

  if (fwd) fctName = fwd_fctName;
  else     fctName = bck_fctName;
  
  /* Set default values */
  
  *maxord = (lmm == CV_ADAMS) ? 12 : 5;
  
  *sld = FALSE;

  *mxsteps = 0;

  *itol = CV_SS;
  *reltol = 1.0e-3;
  *Sabstol = 1.0e-6;
  *Vabstol = NULL;

  *hin = 0.0;
  *hmax = 0.0;
  *hmin = 0.0;

  *rhs_s = FALSE;

  Ng = 0;
  tstopSet = FALSE;
  mon = FALSE;

  *errmsg = TRUE;


  /* Return now if options was empty */

  if (mxIsEmpty(options)) return(0);

  /* User data */

  opt = mxGetField(options,0,"UserData");
  if ( !mxIsEmpty(opt) ) {
    mxDestroyArray(mtlb_data);
    mtlb_data = mxDuplicateArray(opt);
  }
  
  /* Tolerances */

  opt = mxGetField(options,0,"RelTol");
  if ( !mxIsEmpty(opt) ) {
    *reltol = *mxGetPr(opt);
    if (*reltol < 0.0 ) {
      cvmErrHandler(-999, "CVODES", fctName, "RelTol is negative.", NULL);
      return(-1);
    }
  }
    
  opt = mxGetField(options,0,"AbsTol");
  if ( !mxIsEmpty(opt) ) {
    m = mxGetM(opt);
    n = mxGetN(opt);
    if ( (n != 1) && (m != 1) ) {
      cvmErrHandler(-999, "CVODES", fctName, "AbsTol is not a scalar or a vector.", NULL);
      return(-1);
    }
    if ( m > n ) n = m;
    tmp = mxGetPr(opt);
    if (n == 1) {
      *itol = CV_SS;
      *Sabstol = *tmp;
      if (*Sabstol < 0.0) {
        cvmErrHandler(-999, "CVODES", fctName, "AbsTol is negative.", NULL);
      return(-1);
      }
    } else if (n == N) {
      *itol = CV_SV;
      *Vabstol = (double *) malloc(N*sizeof(double));
      for(i=0;i<N;i++) {
        (*Vabstol)[i] = tmp[i];
        if (tmp[i] < 0.0) {
          cvmErrHandler(-999, "CVODES", fctName, "AbsTol has a negative component.", NULL);
          return(-1);
        }
      }
    } else {
      cvmErrHandler(-999, "CVODES", fctName, "AbsTol does not contain N elements.", NULL);
      return(-1);
    }
  }

  /* Maximum number of steps */

  opt = mxGetField(options,0,"MaxNumSteps");
  if ( !mxIsEmpty(opt) ) {
    *mxsteps = (int)*mxGetPr(opt);
    if (*mxsteps < 0) {
      cvmErrHandler(-999, "CVODES", fctName, "MaxNumSteps is negative.", NULL);
      return(-1);
    }
  }

  /* Maximum order */

  opt = mxGetField(options,0,"MaxOrder");
  if ( !mxIsEmpty(opt) ) {
    q = (int)*mxGetPr(opt);
    if (q <= 0) {
      cvmErrHandler(-999, "CVODES", fctName, "MaxOrder must be positive.", NULL);
      return(-1);
    }
    if (q > *maxord) {
      cvmErrHandler(-999, "CVODES", fctName, "MaxOrder is too large for the Method specified.", NULL);
      return(-1);
    }
    *maxord = q;
  }

  /* Initial step size */

  opt = mxGetField(options,0,"InitialStep");
  if ( !mxIsEmpty(opt) ) {
    *hin = *mxGetPr(opt);
  }

  /* Maximum step size */

  opt = mxGetField(options,0,"MaxStep");
  if ( !mxIsEmpty(opt) ) {
    tmp = mxGetPr(opt);
    if (*tmp < 0.0) {
      cvmErrHandler(-999, "CVODES", fctName, "MaxStep is negative.", NULL);
      return(-1);
    }
    if ( mxIsInf(*tmp) ) *hmax = 0.0;
    else                 *hmax = *tmp;
  }

  /* Minimum step size */

  opt = mxGetField(options,0,"MinStep");
  if ( !mxIsEmpty(opt) ) {
    *hmin = *mxGetPr(opt);
    if (*hmin < 0.0) {
      cvmErrHandler(-999, "CVODES", fctName, "MinStep is negative.", NULL);
      return(-1);
    }
  }

  /* Stability Limit Detection */

  opt = mxGetField(options,0,"StabilityLimDet");
  if ( !mxIsEmpty(opt) ) {
    if (!mxIsLogical(opt)) {
      cvmErrHandler(-999, "CVODES", fctName, "StabilityLimDet is not a logical scalar.", NULL);
      return(-1);
    }
    if (mxIsLogicalScalarTrue(opt)) *sld = TRUE;
    else                            *sld = FALSE;
  }

  /* Monitor? */

  opt = mxGetField(options,0,"MonitorFn");
  if ( !mxIsEmpty(opt) ) {
    mon = TRUE;
    mxDestroyArray(mtlb_MONfct);
    mtlb_MONfct = mxDuplicateArray(opt);
    opt = mxGetField(options,0,"MonitorData");
    if ( !mxIsEmpty(opt) ) {
      mxDestroyArray(mtlb_MONdata);
      mtlb_MONdata  = mxDuplicateArray(opt);
    }
  }

  /* The remaining options are interpreted either for 
   * forward problems only or backward problems only */

  if (fwd) {   /* FORWARD PROBLEM ONLY */

    /* Disable error/warning messages? */

    opt = mxGetField(options,0,"ErrorMessages");
    if ( !mxIsEmpty(opt) ) {
      if (!mxIsLogical(opt)) {
        cvmErrHandler(-999, "CVODES", fctName, "ErrorMessages is not a logical scalar.", NULL);
        return(-1);
      }
      if (mxIsLogicalScalarTrue(opt)) *errmsg = TRUE;
      else                            *errmsg = FALSE;
    }

    /* Stopping time */
    opt = mxGetField(options,0,"StopTime");
    if ( !mxIsEmpty(opt) ) {
      *tstop = *mxGetPr(opt);
      tstopSet = TRUE;
    }

    /* Number of root functions */
    opt = mxGetField(options,0,"NumRoots");
    if ( !mxIsEmpty(opt) ) {

      Ng = (int)*mxGetPr(opt);
      if (Ng < 0) {
        cvmErrHandler(-999, "CVODES", fctName, "NumRoots is negative.", NULL);
        return(-1);
      }
      if (Ng > 0) {
        /* Roots function */
        opt = mxGetField(options,0,"RootsFn");
        if ( !mxIsEmpty(opt) ) {
          mxDestroyArray(mtlb_Gfct);
          mtlb_Gfct = mxDuplicateArray(opt);
        } else {
          cvmErrHandler(-999, "CVODES", fctName, "RootsFn required for NumRoots > 0", NULL);
          return(-1);
        }
      }
      
    }

  } else {   /* BACKWARD PROBLEM ONLY */

    /* Dependency on forward sensitivities */

    opt = mxGetField(options,0,"SensDependent");
    if ( !mxIsEmpty(opt) ) {
      if (!mxIsLogical(opt)) {
        cvmErrHandler(-999, "CVODES", fctName, "SensDependent is not a logical scalar.", NULL);
        return(-1);
      }
      if (mxIsLogicalScalarTrue(opt)) *rhs_s = TRUE;
      else                            *rhs_s = FALSE;
    }

  }

  /* We made it here without problems */

  return(0);
}
Пример #19
0
void assignmentoptimal(double *assignment, double *cost, double *distMatrixIn, int nOfRows, int nOfColumns)
{
	double *distMatrix, *distMatrixTemp, *distMatrixEnd, *columnEnd, value, minValue;
	bool *coveredColumns, *coveredRows, *starMatrix, *newStarMatrix, *primeMatrix;
	int nOfElements, minDim, row, col;
#ifdef CHECK_FOR_INF
	bool infiniteValueFound;
	double maxFiniteValue, infValue;
#endif
	
	/* initialization */
	*cost = 0;
	for(row=0; row<nOfRows; row++)
#ifdef ONE_INDEXING
		assignment[row] =  0.0;
#else
		assignment[row] = -1.0;
#endif
	
	/* generate working copy of distance Matrix */
	/* check if all matrix elements are positive */
	nOfElements   = nOfRows * nOfColumns;
	distMatrix    = (double *)mxMalloc(nOfElements * sizeof(double));
	distMatrixEnd = distMatrix + nOfElements;
	for(row=0; row<nOfElements; row++)
	{
		value = distMatrixIn[row];
		if(mxIsFinite(value) && (value < 0))
			mexErrMsgTxt("All matrix elements have to be non-negative.");
		distMatrix[row] = value;
	}

#ifdef CHECK_FOR_INF
	/* check for infinite values */
	maxFiniteValue     = -1;
	infiniteValueFound = false;
	
	distMatrixTemp = distMatrix;
	while(distMatrixTemp < distMatrixEnd)
	{
		value = *distMatrixTemp++;
		if(mxIsFinite(value))
		{
			if(value > maxFiniteValue)
				maxFiniteValue = value;
		}
		else
			infiniteValueFound = true;
	}
	if(infiniteValueFound)
	{
		if(maxFiniteValue == -1) /* all elements are infinite */
			return;
		
		/* set all infinite elements to big finite value */
		if(maxFiniteValue > 0)
			infValue = 10 * maxFiniteValue * nOfElements;
		else
			infValue = 10;
		distMatrixTemp = distMatrix;
		while(distMatrixTemp < distMatrixEnd)
			if(mxIsInf(*distMatrixTemp++))
				*(distMatrixTemp-1) = infValue;
	}
#endif
				
	/* memory allocation */
	coveredColumns = (bool *)mxCalloc(nOfColumns,  sizeof(bool));
	coveredRows    = (bool *)mxCalloc(nOfRows,     sizeof(bool));
	starMatrix     = (bool *)mxCalloc(nOfElements, sizeof(bool));
	primeMatrix    = (bool *)mxCalloc(nOfElements, sizeof(bool));
	newStarMatrix  = (bool *)mxCalloc(nOfElements, sizeof(bool)); /* used in step4 */

	/* preliminary steps */
	if(nOfRows <= nOfColumns)
	{
		minDim = nOfRows;
		
		for(row=0; row<nOfRows; row++)
		{
			/* find the smallest element in the row */
			distMatrixTemp = distMatrix + row;
			minValue = *distMatrixTemp;
			distMatrixTemp += nOfRows;			
			while(distMatrixTemp < distMatrixEnd)
			{
				value = *distMatrixTemp;
				if(value < minValue)
					minValue = value;
				distMatrixTemp += nOfRows;
			}
			
			/* subtract the smallest element from each element of the row */
			distMatrixTemp = distMatrix + row;
			while(distMatrixTemp < distMatrixEnd)
			{
				*distMatrixTemp -= minValue;
				distMatrixTemp += nOfRows;
			}
		}
		
		/* Steps 1 and 2a */
		for(row=0; row<nOfRows; row++)
			for(col=0; col<nOfColumns; col++)
				if(distMatrix[row + nOfRows*col] == 0)
					if(!coveredColumns[col])
					{
						starMatrix[row + nOfRows*col] = true;
						coveredColumns[col]           = true;
						break;
					}
	}
	else /* if(nOfRows > nOfColumns) */
	{
		minDim = nOfColumns;
		
		for(col=0; col<nOfColumns; col++)
		{
			/* find the smallest element in the column */
			distMatrixTemp = distMatrix     + nOfRows*col;
			columnEnd      = distMatrixTemp + nOfRows;
			
			minValue = *distMatrixTemp++;			
			while(distMatrixTemp < columnEnd)
			{
				value = *distMatrixTemp++;
				if(value < minValue)
					minValue = value;
			}
			
			/* subtract the smallest element from each element of the column */
			distMatrixTemp = distMatrix + nOfRows*col;
			while(distMatrixTemp < columnEnd)
				*distMatrixTemp++ -= minValue;
		}
		
		/* Steps 1 and 2a */
		for(col=0; col<nOfColumns; col++)
			for(row=0; row<nOfRows; row++)
				if(distMatrix[row + nOfRows*col] == 0)
					if(!coveredRows[row])
					{
						starMatrix[row + nOfRows*col] = true;
						coveredColumns[col]           = true;
						coveredRows[row]              = true;
						break;
					}
		for(row=0; row<nOfRows; row++)
			coveredRows[row] = false;
		
	}	
	
	/* move to step 2b */
	step2b(assignment, distMatrix, starMatrix, newStarMatrix, primeMatrix, coveredColumns, coveredRows, nOfRows, nOfColumns, minDim);

	/* compute cost and remove invalid assignments */
	computeassignmentcost(assignment, cost, distMatrixIn, nOfRows);
	
	/* free allocated memory */
	mxFree(distMatrix);
	mxFree(coveredColumns);
	mxFree(coveredRows);
	mxFree(starMatrix);
	mxFree(primeMatrix);
	mxFree(newStarMatrix);

	return;
}
Пример #20
0
  /* Function: mdlCheckParameters =============================================
   * Abstract:
   *    Validate our parameters to verify they are okay.
   */
  static void mdlCheckParameters(SimStruct *S)
  {
	  int_T i;
	  static char_T msg[100];

/* for RTW we do not need these variables */
#ifdef MATLAB_MEX_FILE
	const char *fname;
	mxArray *fval;
	int_T nfields;
#endif

	  /* Check 1st parameter: number of states */
      {
	      if ( !mxIsDouble(ssGetSFcnParam(S,0)) || 
		   mxIsEmpty(ssGetSFcnParam(S,0)) ||
		   mxGetNumberOfElements(ssGetSFcnParam(S,0))!=1 ||
		   mxGetScalar(ssGetSFcnParam(S,0))<=0 || 
		   mxIsNaN(*mxGetPr(ssGetSFcnParam(S,0))) || 
		   mxIsInf(*mxGetPr(ssGetSFcnParam(S,0))) ||
		   mxIsSparse(ssGetSFcnParam(S,0)) )  {
		      ssSetErrorStatus(S,"lcp_sfun: Number of states must be of type double, not empty, scalar and finite.");
		      return;
	      }
      }
 
      /* Check 2nd parameter: sample time */
      {
	      if ( !mxIsDouble(ssGetSFcnParam(S,1)) || 
		   mxIsEmpty(ssGetSFcnParam(S,1)) ||
		   mxGetNumberOfElements(ssGetSFcnParam(S,1))!=1 ||
		   mxGetScalar(ssGetSFcnParam(S,1))<=0 || 
		   mxIsNaN(*mxGetPr(ssGetSFcnParam(S,1))) || 
		   mxIsInf(*mxGetPr(ssGetSFcnParam(S,1))) ||
		   mxIsSparse(ssGetSFcnParam(S,1)) )  {
		      ssSetErrorStatus(S,"lcp_sfun: Sample time must be of type double, not empty, scalar and finite.");
		      return;
	      }
      }

#ifdef MATLAB_MEX_FILE
      /* Check 3rd parameter: options */
      if (ssGetSFcnParamsCount(S)==3) 
      {
	      if (!mxIsStruct(ssGetSFcnParam(S,2))) {
		      ssSetErrorStatus(S, "lcp_sfun: Options must be in STRUCT format.");
		      return;
	      }      
	      else if (mxGetNumberOfElements(ssGetSFcnParam(S,2))>1) {
		      ssSetErrorStatus(S,"lcp_sfun: Only one option structure is allowed.");
		      return;
	      }
	      /* checking each option individually */
	      nfields = mxGetNumberOfFields(ssGetSFcnParam(S,2));
	      for (i=0; i<nfields; i++) {
		      fname = mxGetFieldNameByNumber(ssGetSFcnParam(S,2), i);
		      fval = mxGetField(ssGetSFcnParam(S,2), 0, fname);
			/* check for proper field names */
			if (!( (strcmp(fname, "zerotol")==0) || (strcmp(fname, "maxpiv")==0) ||
			       (strcmp(fname, "lextol")==0) || (strcmp(fname, "nstepf")==0) ||
			       (strcmp(fname, "clock")==0) || (strcmp(fname, "verbose")==0) ||
			       (strcmp(fname, "routine")==0) || (strcmp(fname, "timelimit")==0) ||
			       (strcmp(fname, "normalize")==0) || (strcmp(fname, "normalizethres")==0) )) {
				strcpy(msg,"");
				strcat(msg, "lcp_sfun: The field '");
				strcat(msg, fname);
				strcat(msg, "' is not allowed in the options structure.");
				ssSetErrorStatus(S, msg);
				return;
			}
			/* some options must be nonnegative */
			if (strcmp(fname,"zerotol")==0 || strcmp(fname,"maxpiv")==0 ||
			    strcmp(fname,"timelimit")==0 || strcmp(fname,"lextol")==0 ||
			     (strcmp(fname,"nstepf")==0) || (strcmp(fname, "normalizethres")==0) ) {
				if (!mxIsDouble(fval) || mxIsEmpty(fval) || (mxGetM(fval)*mxGetN(fval))!=1 ||
				    (mxGetScalar(fval)<=0) ) {	  
					strcpy(msg,"");
					strcat(msg, "lcp_sfun: Option value '");
					strcat(msg, fname);
					strcat(msg, "' must be of type double, nonempty, scalar, and nonnegative.");
					ssSetErrorStatus(S, msg);
					return;
				}
			}
			/* some can be zeros */
			if (strcmp(fname,"clock")==0 || strcmp(fname,"verbose")==0 ||
			    strcmp(fname,"routine")==0 || strcmp(fname,"normalize")==0) {
				if (!mxIsDouble(fval) || mxIsEmpty(fval) || (mxGetM(fval)*mxGetN(fval))!=1 ) {	  
					strcpy(msg,"");
					strcat(msg, "lcp_sfun: Option value '");
					strcat(msg, fname);
					strcat(msg, "' must be of type double, nonempty, scalar, and integer valued.");
					ssSetErrorStatus(S, msg);
					return;
				}
			}
			/* No NaN values allowed */
			if ( mxIsNaN(*mxGetPr(fval)) ) {
				ssSetErrorStatus(S, "lcp_sfun: No 'NaN' are allowed in the options structure.");
				return;
			}
			/* Inf value allowed only for timelimit */
			if ( strcmp(fname,"timelimit")!=0 && mxIsInf(*mxGetPr(fval)) ) {
				ssSetErrorStatus(S, "lcp_sfun: No 'Inf' terms allowed except for 'timelimit' option.");
				return;
			}
	      }
      }
#endif
    
  }
Пример #21
0
Файл: mfwt.c Проект: uniomni/CV
void mexFunction(int nlhs, mxArray *plhs[],
                 int nrhs, const mxArray *prhs[])
{
  int i, j, k, M, N, NH, index, D, lambda, Coarsest_level, pwr;
  int dir, row;
  double *X, *Y, *lp, *hp;
  

  /****************************/  
  /* A very basic input check */
  /****************************/
  if ( nrhs != 4 )
    mexErrMsgTxt("Four inputs required!");
  else if ( nlhs > 1 )
    mexErrMsgTxt("Too many output arguments!");  
    

  /*******************************************/
  /* Get input matrix from MATLAB argument 1 */
  /*******************************************/
  M = mxGetM(prhs[0]);   /* Number of rows         */
  N = mxGetN(prhs[0]);   /* Number of columns      */
  X = mxGetPr(prhs[0]);	 /* The input M x N matrix */			 

  
  /***************************************************************/  
  /* Get wavelet transform depth, lambda, from MATLAB argument 2 */
  /***************************************************************/
  lambda = (int) mxGetScalar(prhs[1]);
  if (mxIsInf(mxGetScalar(prhs[1])))
    {                      /* If requested depth == Inf then */         
      Coarsest_level = 1;    /* take as many steps as possible */
  } else
  {
    pwr = pow(2,lambda);      
    Coarsest_level = max((int) (N/ (float) pwr), 1);      
  }
  
  /****************************************************/
  /* Get wavelet filters from MATLAB argument 3 and 4 */
  /****************************************************/  
  D = max(mxGetM(prhs[2]),mxGetN(prhs[2]));   /* Filter length */
  if (D != max(mxGetM(prhs[3]),mxGetN(prhs[3]))) 
    mexErrMsgTxt("Filters must have same length. Pad with zeros!");      
  
  lp = mxGetPr(prhs[2]); /* Low pass filter  */
  hp = mxGetPr(prhs[3]); /* High pass filter */
  
  /************************************************************/
  /* Create output array. This will also be used as workspace */
  /************************************************************/  
  plhs[0] = mxCreateDoubleMatrix(M, N, mxREAL);
  Y = mxGetPr(plhs[0]);	   
  	

  /***************************************/	
  /* Outer loop of the wavelet transform */
  /***************************************/	
  
  dir = 0; /* Alternate transform direction to save space */
  
  while (N % 2 == 0 && N > Coarsest_level) { /* Transform for decreasing N */ 
    dir = 1 - dir;
    if (dir == 1) {    
      NH = mpwt (X, M, N, lp, hp, D, Y);  /* One-step transform X -> Y */      
    } else {
      NH = mpwt (Y, M, N, lp, hp, D, X);  /* One-step transform Y -> X */      
      for (k = NH; k < N; k++) {          /* Copy partial result to Y  */ 
	index = k*M;      
        for (row = 0; row < M; row++) {
	  Y[index] = X[index];
	  index++;
	}    
      }   
    }
    N = NH;                               /* N = N/2 */
  }
  
  if (dir == 0) {                    /* If last transform was backwards */
    for (k = 0; k < N; k++) {
      index = k*M;      
      for (row = 0; row < M; row++) {
    	Y[index] = X[index];         /* then copy dc term to Y */
    	index++;
      }    
    } 
  }    
} /* END MATLAB GATEWAY ROUTINE */		 
Пример #22
0
//Check all inputs for size and type errors
void checkInputs(const mxArray *prhs[], int nrhs)
{
    size_t ndec, m, i;
    const mxArray *fxd;
    double *val;
    
    //Correct number of inputs
    if(nrhs < 3)
        mexErrMsgTxt("You must supply at least 3 arguments to dsdp (f, A, b)"); 
    
    //Check we have an objective
    if(mxIsEmpty(pF))
        mexErrMsgTxt("You must supply an objective function via f!");
    
    //Check we have some constraints
    if(nrhs >= (eSDP+1) && mxIsEmpty(pA) && mxIsEmpty(pLB) && mxIsEmpty(pUB) && mxIsEmpty(pSDP))
        mexErrMsgTxt("You must supply constraints to this solver!");
    else if(nrhs == (eUB+1) && mxIsEmpty(pA) && mxIsEmpty(pLB) && mxIsEmpty(pUB))
        mexErrMsgTxt("You must supply constraints to this solver!");
    else if(nrhs == (eB+1) && (mxIsEmpty(pA) || mxIsEmpty(pB)))
        mexErrMsgTxt("You must supply constraints to this solver!");
    
    //Check options is a structure
    if(nrhs > eOPTS && !mxIsStruct(pOPTS))
        mexErrMsgTxt("The options argument must be a structure");
    
    //Get Sizes
    ndec = mxGetNumberOfElements(pF);
    
    //Check linear constraints
    if(!mxIsEmpty(pA)) {
        //Check types
        if(!mxIsSparse(pA) || mxIsComplex(pA) || !mxIsDouble(pA))
            mexErrMsgTxt("A must be real, sparse, double matrix");
        if(mxIsSparse(pB) || mxIsComplex(pB) || !mxIsDouble(pB))
            mexErrMsgTxt("b must be real, dense, double column vector");
        //Check sizes
        if(mxGetN(pA) != ndec)
            mexErrMsgTxt("A does not have the same number of columns as decision variables!");
        if(mxGetM(pA) != mxGetNumberOfElements(pB))
            mexErrMsgTxt("A and b do not have the same number of rows!");        
    }
    //Check bounds
    if(nrhs > eLB && !mxIsEmpty(pLB)) {
        if(mxIsSparse(pLB) || mxIsComplex(pLB) || !mxIsDouble(pLB))
            mexErrMsgTxt("lb must be real, dense, double column vector");
        if(mxGetNumberOfElements(pLB) != ndec)
            mexErrMsgTxt("lb is not the same length as f!");
    }
    if(nrhs > eUB && !mxIsEmpty(pUB)) {
        if(mxIsSparse(pUB) || mxIsComplex(pUB) || !mxIsDouble(pUB))
            mexErrMsgTxt("ub must be real, dense, double column vector");
        if(mxGetNumberOfElements(pUB) != ndec)
            mexErrMsgTxt("ub is not the same length as f!");
    }
    //Check sdcones
    if(nrhs > eSDP && !mxIsEmpty(pSDP)) {
        if(mxIsCell(pSDP)) {
            for(i=0;i<mxGetNumberOfElements(pSDP);i++)
                checkCone(mxGetCell(pSDP,i),ndec,i);
        }
        else
            checkCone(pSDP,ndec,1);        
    }
    //Check y0
    if(nrhs > eY0 && !mxIsEmpty(pY0)) {
        if(mxIsSparse(pY0) || mxIsComplex(pY0) || !mxIsDouble(pY0))
            mexErrMsgTxt("y0 must be real, dense, double column vector");
        if(mxGetNumberOfElements(pY0) != ndec)
            mexErrMsgTxt("y0 is not the same length as f!");
    }
    //Check fixed vars option
    if(nrhs > eOPTS && !mxIsEmpty(pOPTS) && mxGetField(pOPTS,0,"fixed") && !mxIsEmpty(mxGetField(pOPTS,0,"fixed"))) {
        fxd = mxGetField(pOPTS,0,"fixed");
        //Check Type
        if(mxIsSparse(fxd) || mxIsComplex(fxd) || !mxIsDouble(fxd))
            mexErrMsgTxt("The fixed option must be a real, dense, double matrix");
        val = mxGetPr(fxd);
        m = mxGetM(fxd);
        if(mxGetN(fxd) != 2)
            mexErrMsgTxt("The fixed option must contain 2 columns");
        if(m > ndec)
            mexErrMsgTxt("The fixed option must not contain more rows than decision variables");
        for(i=0;i<m;i++) {
            if(val[i] <= 0 || val[i] > ndec)
                mexErrMsgTxt("A variable index in the fixed option is <= 0 or > ndec");
            if(mxIsNaN(val[i+m]) || mxIsInf(val[i+m]))
                mexErrMsgTxt("A variable value in the fixed option is NaN or Inf");            
        }
    }
}
Пример #23
0
//Main Function
void mexFunction(int nlhs, mxArray *plhs[],int nrhs, const mxArray *prhs[])
{
    //Input Args
    double *f, *A = NULL, *b = NULL, *lb = NULL, *ub = NULL, *y0 = NULL;
    double *sdpDIM = NULL, *SDP_pr = NULL;
    
    //Return Args
    double *x, *pval, *dval, *exitflag, *iter, *pdflag;
    
    //Options (most get defaults written in)
    int maxiter = 1500;  
    int reuse=4,rpos=0,drho=1,ndim,sdpnmax=1;
    double penalty,rho,dbound,dlbound,zbar,r0,mu0,ylow,yhigh,gaptol,pnormtol,maxtrust,steptol,inftol,infptol;
    double lpb=1.0, datanorm[3], *dreuse, *fixed = NULL;
    
    //Internal Vars
    size_t nlincon = 0, ndec = 0, ncones = 0, nfix = 0;
    size_t lincon_nz = 0;    
    size_t i, j;
    size_t nLB = 0, nUB = 0;
    int *temp_ir = NULL, *temp_jc = NULL;
    double *temp_pr = NULL;
    const char *onames[2] = {"pval","dval"};
    const char *fnames[11] = {"iter","pdflag","r","mu","pstep","dstep","pnorm","ynorm","tracex","reuse","rho"};    
    double evaltime, *X = NULL;
    int iters = 0, status, indcell = 0;
    
    //DSDP Vars
    DSDP dsdp;
    SDPCone sdpcone = NULL;
    LPCone lpcone   = NULL;
    BCone bcone     = NULL;
    DSDPTerminationReason reason;
    DSDPSolutionType pdfeasible;  

    //Sparse Indicing
    mwIndex *A_ir, *A_jc;
    //Version Return
    if(nrhs < 1) {
        if(nlhs < 1)
            printSolverInfo();
        else
            plhs[0] = mxCreateString(DSDP_VERSION);
        return;
    }        
    
    //Check Inputs
    checkInputs(prhs,nrhs); 
    
    //Get pointers to Input variables
	f = mxGetPr(pF); ndec = mxGetNumberOfElements(pF);
    if(!mxIsEmpty(pA)) {
        A = mxGetPr(pA); 
        A_ir = mxGetIr(pA);
        A_jc = mxGetJc(pA);
        b = mxGetPr(pB);
        nlincon = mxGetM(pA);
        lincon_nz = A_jc[mxGetN(pA)];
    }
    if(nrhs > eLB && !mxIsEmpty(pLB))
        lb = mxGetPr(pLB); 
    if(nrhs > eUB && !mxIsEmpty(pUB))
        ub = mxGetPr(pUB);
    if(nrhs > eSDP && !mxIsEmpty(pSDP)) {
        if(mxIsCell(pSDP))
            ncones = mxGetNumberOfElements(pSDP);
        else
            ncones = 1;
    }
    if(nrhs > eY0 && !mxIsEmpty(pY0))
        y0 = mxGetPr(pY0);
    if(nrhs > eOPTS && !mxIsEmpty(pOPTS) && mxGetField(pOPTS,0,"fixed") && !mxIsEmpty(mxGetField(pOPTS,0,"fixed"))) {
        fixed = mxGetPr(mxGetField(pOPTS,0,"fixed"));
        nfix = mxGetM(mxGetField(pOPTS,0,"fixed")); 
    }
    
    //Create Outputs
    plhs[0] = mxCreateDoubleMatrix(ndec,1, mxREAL);
    plhs[1] = mxCreateStructMatrix(1,1,2,onames);
    mxSetField(plhs[1],0,onames[0],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[1],0,onames[1],mxCreateDoubleMatrix(1,1, mxREAL));
    plhs[2] = mxCreateDoubleMatrix(1,1, mxREAL);   
    x = mxGetPr(plhs[0]); 
    pval = mxGetPr(mxGetField(plhs[1],0,onames[0]));
    dval = mxGetPr(mxGetField(plhs[1],0,onames[1]));
    exitflag = mxGetPr(plhs[2]);    
    //Info Output    
    plhs[3] = mxCreateStructMatrix(1,1,11,fnames);
    mxSetField(plhs[3],0,fnames[0],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[3],0,fnames[1],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[3],0,fnames[2],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[3],0,fnames[3],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[3],0,fnames[4],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[3],0,fnames[5],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[3],0,fnames[6],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[3],0,fnames[7],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[3],0,fnames[8],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[3],0,fnames[9],mxCreateDoubleMatrix(1,1, mxREAL));
    mxSetField(plhs[3],0,fnames[10],mxCreateDoubleMatrix(1,1, mxREAL));
    iter = mxGetPr(mxGetField(plhs[3],0,fnames[0]));
    pdflag = mxGetPr(mxGetField(plhs[3],0,fnames[1]));   
    dreuse = mxGetPr(mxGetField(plhs[3],0,"reuse"));
    if(nlhs > 4)         
    	plhs[4] = mxCreateCellMatrix(ncones+(int)(nlincon>0)+(int)(nfix>0),1);        
    
    //Set Defaults
    maxtime = 1000;
    printLevel = 0;
    
    //Create DSDP Problem
    DSDP_ERR( DSDPCreate((int)ndec,&dsdp), "Error Creating DSDP Problem");
    //Set Monitor
    DSDP_ERR( DSDPSetMonitor(dsdp,DSDPMonitor,0), "Error Setting DSDP Monitor");
    
    //Set Dual Objective
    for (i=0;i<ndec;i++){
        DSDP_ERR( DSDPSetDualObjective(dsdp,(int)i+1,f[i]), "Error Adding Objective Coefficients"); }
    
    //Check finite bounds for allocation
    if(lb || ub)
        for(i=0;i<ndec;i++) {
            if(lb)
                if(!mxIsInf(lb[i]))
                    nLB++;
            if(ub)
                if(!mxIsInf(ub[i]))
                    nUB++;
        }
    
    //Set Bounds as BCone
    if(nLB || nUB) {
        DSDP_ERR( DSDPCreateBCone(dsdp, &bcone), "Error creating BCone");
        DSDP_ERR( BConeAllocateBounds(bcone, (int)(nLB+nUB)), "Error allocating bounds");        
        for(i=0;i<ndec;i++) {
            if(nLB > 0 && !mxIsInf(lb[i]))
                DSDP_ERR( BConeSetLowerBound(bcone, (int)i+1, lb[i]), "Error setting lower bound");
            if(nUB > 0 && !mxIsInf(ub[i]))
                DSDP_ERR( BConeSetUpperBound(bcone, (int)i+1, ub[i]), "Error setting upper bound");
        }
    }
    
    //Set Linear Inequality Constraints as LPCone
    if(nlincon) {
        int M = (int)mxGetM(pA);
        int N = (int)mxGetN(pA);
        DSDP_ERR( DSDPCreateLPCone(dsdp, &lpcone), "Error creating LPCone (inequalities)");
        //Create Memory to store A*x <= b in dsdp and integer format
        temp_jc = mxCalloc(N+2,sizeof(int));
        temp_ir = mxCalloc(lincon_nz+M,sizeof(int));
        temp_pr = mxCalloc(lincon_nz+M,sizeof(double));
        //Copy over linear A
        for(i=0;i<=(size_t)N;i++)
            temp_jc[i] = (int)A_jc[i];
        for(i=0;i<lincon_nz;i++) {
            temp_ir[i] = (int)A_ir[i];
            temp_pr[i] = A[i];
        }
        //Append linear rhs (b)
        temp_jc[N+1] = temp_jc[N] + M;
        for(i=lincon_nz,j=0;j<(size_t)M;j++) {
            if(b[j] != 0) {
                temp_ir[i] = (int)j;
                temp_pr[i++] = b[j];
            }
            else
                temp_jc[N+1]--;
        }
        #ifdef DEBUG
            mexPrintf("---- Inequality Constraints ----\n");
            for(i=0;i<=(size_t)(N+1);i++)
                mexPrintf("jc[%d] = %d\n",i,temp_jc[i]);
            for(i=0;i<lincon_nz+M;i++)
                mexPrintf("ir[%d] = %d, pr[%d] = %f\n",i,temp_ir[i],i,temp_pr[i]);
        #endif        
        //Set LP Cone Data
        DSDP_ERR( LPConeSetData2(lpcone, M, temp_jc, temp_ir, temp_pr), "Error setting LP Cone data (inequality)" );
        //Optionally set X data
        if(nlhs > 4) {
            mxSetCell(plhs[4],indcell,mxCreateDoubleMatrix(M,1,mxREAL));
            DSDP_ERR( LPConeSetXVec(lpcone,mxGetPr(mxGetCell(plhs[4],indcell++)),M), "Error setting LP Cone X data" );
        }
    }
    
    //Set Semidefinite Constraints as SDPCone
    if(ncones) {
        //Create the cone structure, specifying each constraint as a block
        DSDP_ERR( DSDPCreateSDPCone(dsdp,(int)ncones,&sdpcone), "Error creating SDPCone");
        //Add each constraint cone
        for(i=0;i<ncones;i++) {
            if(ncones == 1 && !mxIsCell(pSDP)) {
                if(nlhs > 4) {
                    mxSetCell(plhs[4],indcell,mxCreateDoubleMatrix(mxGetM(pSDP),1,mxREAL));
                    X = mxGetPr(mxGetCell(plhs[4],indcell++));
                }
                ndim = addSDPCone(sdpcone,pSDP,(int)i,X);
            }
            else {
                if(nlhs > 4) {
                    mxSetCell(plhs[4],indcell,mxCreateDoubleMatrix(mxGetM(mxGetCell(pSDP,i)),1,mxREAL));
                    X = mxGetPr(mxGetCell(plhs[4],indcell++));
                }
                ndim = addSDPCone(sdpcone,mxGetCell(pSDP,i),(int)i,X);
            }
            //Update max dim
            if(sdpnmax < ndim)
                sdpnmax = ndim;
        }
    }
    
    //Set y0
    if (y0)
        for (i=0;i<ndec;i++) {
            DSDP_ERR( DSDPSetY0(dsdp,(int)i+1,y0[i]), "Error setting Y0");            
        }
    
    //Determine whether to reuse schur complement matrix (dsdp authors' heuristic)
    if(ndec == 1)
        reuse = 1/sdpnmax;
    else
        reuse = ((int)ndec-2)/sdpnmax; 
    if (ndec<50 && reuse==0) reuse=1;
    if (reuse>=1) reuse++;
    reuse=reuse*reuse;
    if (ndec<2000 && ndec>10) reuse=10;
    if (ndec>12) reuse=12;    
    
    //Get DSDP Default Options
    DSDP_ERR( DSDPGetR(dsdp,&r0), "Error Getting R");
    DSDP_ERR( DSDPGetPenaltyParameter(dsdp,&penalty), "Error Getting Penalty Parameter");
    DSDP_ERR( DSDPGetPotentialParameter(dsdp,&rho), "Error Getting Potential Parameter");
    DSDP_ERR( DSDPGetDualBound(dsdp,&dbound), "Error Getting Dual Bound");
    DSDP_ERR( DSDPGetGapTolerance(dsdp,&gaptol), "Error Getting Gap Tolerance");
    DSDP_ERR( DSDPGetRTolerance(dsdp,&inftol), "Error Getting R Tolerance");
    DSDP_ERR( DSDPGetBarrierParameter(dsdp,&mu0), "Error Getting Barrier Parameter");
    DSDP_ERR( DSDPGetMaxTrustRadius(dsdp,&maxtrust), "Error Getting Max Trust Radius");
    DSDP_ERR( DSDPGetStepTolerance(dsdp,&steptol), "Error Getting Step Tolerance");
    DSDP_ERR( DSDPGetPTolerance(dsdp,&infptol), "Error Getting P Tolerance");
    DSDP_ERR( DSDPGetPNormTolerance(dsdp,&pnormtol), "Error Getting PNorm Tolerance");
    
    //Get Data Norms to establish y bounds
    DSDP_ERR( DSDPGetDataNorms(dsdp, datanorm), "Error Getting Data Norms");
    DSDP_ERR( DSDPGetYBounds(dsdp,&ylow,&yhigh), "Error Getting Y Bounds");
    if (datanorm[0]==0){DSDP_ERR( DSDPSetYBounds(dsdp,-1.0,1.0), "Error Setting Y Bounds");}
    
    //Get User Options (overwrites defaults above)
    if(nrhs > eOPTS && !mxIsEmpty(pOPTS)) {
        //OPTI Options
        GetIntegerOption(pOPTS,"maxiter",&maxiter);
        GetDoubleOption(pOPTS,"maxtime",&maxtime);
        GetIntegerOption(pOPTS,"display",&printLevel);
        //DSDP Options
        GetDoubleOption(pOPTS,"r0",&r0);
        GetDoubleOption(pOPTS,"penalty",&penalty);
        GetDoubleOption(pOPTS,"rho",&rho);
        GetDoubleOption(pOPTS,"dbound",&dbound);
        GetDoubleOption(pOPTS,"gaptol",&gaptol);
        GetDoubleOption(pOPTS,"rtol",&inftol);
        GetDoubleOption(pOPTS,"mu0",&mu0);
        GetDoubleOption(pOPTS,"maxtrust",&maxtrust);
        GetDoubleOption(pOPTS,"steptol",&steptol);
        GetDoubleOption(pOPTS,"ptol",&infptol);
        GetDoubleOption(pOPTS,"pnormtol",&pnormtol); 
        GetIntegerOption(pOPTS,"reuse",&reuse);
        GetIntegerOption(pOPTS,"rpos",&rpos);
        GetIntegerOption(pOPTS,"drho",&drho);
        //Check and set DSDP options without valid defaults
        if(mxGetField(pOPTS,0,"zbar") && !mxIsEmpty(mxGetField(pOPTS,0,"zbar"))) {
            GetDoubleOption(pOPTS,"zbar",&zbar);
            DSDP_ERR( DSDPSetZBar(dsdp,zbar), "Error Setting Z Bar");
        }
        if(mxGetField(pOPTS,0,"dlbound") && !mxIsEmpty(mxGetField(pOPTS,0,"dlbound"))) {
            GetDoubleOption(pOPTS,"dlbound",&dlbound);
            DSDP_ERR( DSDPSetDualLowerBound(dsdp,dlbound), "Error Setting Dual Lower Bound");
        }
        if(mxGetField(pOPTS,0,"ybound") && !mxIsEmpty(mxGetField(pOPTS,0,"ybound"))) {
            GetDoubleOption(pOPTS,"ybound",&yhigh); ylow = -yhigh;
            DSDP_ERR( DSDPSetYBounds(dsdp,ylow,yhigh), "Error Setting Y Bounds");
        }
    }

    //Set DSDP Options with Defaults
    DSDP_ERR( DSDPSetMaxIts(dsdp,maxiter), "Error Setting Max Iterations");    
    DSDP_ERR( DSDPSetR0(dsdp,r0), "Error Setting Option R0 ");        
    DSDP_ERR( DSDPSetPenaltyParameter(dsdp,penalty), "Error Setting Penalty Parameter");
    DSDP_ERR( DSDPSetPotentialParameter(dsdp,rho), "Error Setting Potential Parameter");
    DSDP_ERR( DSDPSetDualBound(dsdp,dbound), "Error Setting Dual Bound");
    DSDP_ERR( DSDPSetGapTolerance(dsdp,gaptol), "Error Setting Gap Tolerance");
    DSDP_ERR( DSDPSetRTolerance(dsdp,inftol), "Error Setting R Tolerance");
    DSDP_ERR( DSDPSetBarrierParameter(dsdp,mu0), "Error Setting Barrier Parameter");
	DSDP_ERR( DSDPSetMaxTrustRadius(dsdp,maxtrust), "Error Setting Max Trust Radius");
	DSDP_ERR( DSDPSetStepTolerance(dsdp,steptol), "Error Setting Step Tolerance")
    DSDP_ERR( DSDPSetPTolerance(dsdp,infptol), "Error Setting P Tolerance");
    DSDP_ERR( DSDPSetPNormTolerance(dsdp,pnormtol), "Error Setting PNorm Tolerance");   
    if(reuse < 0) reuse = 0; if(reuse > 15) reuse = 15;
    DSDP_ERR( DSDPReuseMatrix(dsdp,reuse), "Error Setting Reuse Matrix");    
    //Set Other DSDP Options
    DSDP_ERR( DSDPUsePenalty(dsdp,rpos), "Error Setting Use Penalty");
    DSDP_ERR( DSDPUseDynamicRho(dsdp,drho), "Error Setting Dynamic Rho");    
    if (lpb<0.1) lpb=0.1;
    if(lpcone) DSDP_ERR( LPConeScaleBarrier(lpcone,lpb), "Error Setting LPCone Scale Barrier");   
    
    //Set Fixed Variables
    if(fixed != NULL) {
        if(nlhs > 4) {            
            mxSetCell(plhs[4],indcell,mxCreateDoubleMatrix(nfix,1,mxREAL));
            X = mxGetPr(mxGetCell(plhs[4],indcell++));
        }
        else
            X = NULL;
        DSDP_ERR( DSDPSetFixedVariables(dsdp, fixed, &fixed[nfix], X, (int)nfix), "Error Setting Fixed Variables");
    }
    
    //Print Header
    if(printLevel) {
        mexPrintf("\n------------------------------------------------------------------\n");
        mexPrintf(" This is DSDP v%s\n",DSDP_VERSION); 
        mexPrintf(" Authors: Steve Benson, Yinyu Ye and Xiong Zhang\n\n");
        mexPrintf(" Problem Properties:\n");
        mexPrintf(" # Decision Variables:        %4d\n",ndec);
        mexPrintf(" # Linear Inequalities:       %4d ",nlincon);
        if(nlincon)
            mexPrintf("[%d nz]\n",lincon_nz);
        else
            mexPrintf("\n");        
        mexPrintf(" # Semidefinite Cones:        %4d\n",ncones);

        mexPrintf("------------------------------------------------------------------\n");
    }
    
    //Start timer
    start = clock();
    //Call DSDP Setup to initialize problem
    DSDP_ERR( DSDPSetup(dsdp), "Error setting up DSDP Problem, likely out of memory");
    //Now Solve the Problem
    status = DSDPSolve(dsdp);
    //Stop Timer
    end = clock();
    evaltime = ((double)(end-start))/CLOCKS_PER_SEC;
    //Determine Stop Reason
    if(status == 0) {
        DSDP_ERR( DSDPStopReason(dsdp,&reason), "Error retrieving post-solve stop reason"); }
    else if(status == DSDP_MAX_TIME || status == DSDP_USER_TERMINATION)
        reason = status;
    else {
        DSDP_ERR( status, "Error solving DSDP Problem!");}
    
    //Computer X and Get Solution Type
    if (reason!=DSDP_INFEASIBLE_START)
        DSDP_ERR( DSDPComputeX(dsdp), "Error computing post-solve x");
    DSDP_ERR( DSDPGetSolutionType(dsdp,&pdfeasible), "Error collecting post-solve solution type");
    
    //Copy Dual Solution
    DSDP_ERR( DSDPGetY(dsdp,x,(int)ndec), "Error returning Solution Vector");
    //Collect Output Statistics
    DSDPGetIts(dsdp,&iters);     
    DSDPGetDObjective(dsdp,dval);    
    DSDPGetPObjective(dsdp,pval);    
    DSDPGetR(dsdp,mxGetPr(mxGetField(plhs[3],0,"r")));
    DSDPGetBarrierParameter(dsdp,mxGetPr(mxGetField(plhs[3],0,"mu")));
    DSDPGetStepLengths(dsdp,mxGetPr(mxGetField(plhs[3],0,"pstep")),mxGetPr(mxGetField(plhs[3],0,"dstep")));
    DSDPGetPnorm(dsdp,mxGetPr(mxGetField(plhs[3],0,"pnorm")));
    DSDPGetYMaxNorm(dsdp,mxGetPr(mxGetField(plhs[3],0,"ynorm")));
    DSDPGetTraceX(dsdp,mxGetPr(mxGetField(plhs[3],0,"tracex")));
    DSDPGetPotentialParameter(dsdp,mxGetPr(mxGetField(plhs[3],0,"rho")));
    *dreuse = (double)reuse;
    
    //Assign to MATLAB
    *iter = (double)iters;    
    *exitflag = (double)reason;
    *pdflag = (double)pdfeasible;
    
    //Print Header
    if(printLevel){            
        //Detail termination reason
        switch(reason)
        {
            //Success
            case DSDP_CONVERGED:	
                mexPrintf("\n *** DSDP CONVERGED ***\n");  break;
            case DSDP_UPPERBOUND:
                mexPrintf("\n *** DSDP CONVERGED: Dual Objective exceeds its bound***\n"); break;
            //Error
            case DSDP_SMALL_STEPS:
                mexPrintf("\n *** TERMINATION: EARLY EXIT ***\n *** CAUSE: Terminated due to Small Steps ***\n"); break;
            case DSDP_MAX_IT:
                mexPrintf("\n *** TERMINATION: EARLY EXIT ***\n *** CAUSE: Maximum Iterations Reached ***\n"); break;
            case DSDP_MAX_TIME:
                mexPrintf("\n *** TERMINATION: EARLY EXIT ***\n *** CAUSE: Maximum Time Reached ***\n"); break;
            case DSDP_INFEASIBLE_START:
                mexPrintf("\n *** TERMINATION: EARLY EXIT ***\n *** CAUSE: Infeasible Starting Point ***\n"); break;
            case DSDP_USER_TERMINATION:
                mexPrintf("\n *** TERMINATION: EARLY EXIT ***\n *** CAUSE: User Exited ***\n"); break;            
            //Here is ok too?
            default:
                mexPrintf("\n *** DSDP FINISHED ***\n"); break;
        }
        //Detail solution status
        if(reason == DSDP_CONVERGED || reason == DSDP_UPPERBOUND) {
            switch(pdfeasible)
            {
                //Success
                case DSDP_PDFEASIBLE:
                    mexPrintf(" Solution Status: Both Primal and Dual are Feasible and Bounded\n"); break;             
                //Error
                case DSDP_UNBOUNDED:
                    mexPrintf(" Solution Status: Dual Unbounded, Primal Infeasible\n"); break;
                case DSDP_INFEASIBLE:
                    mexPrintf(" Solution Status: Primal Unbounded, Dual Infeasible\n"); break;
                case DSDP_PDUNKNOWN:
                default:
                    mexPrintf(" Solution Status: Unknown - Check Dual Bounds\n"); break;
            }
        }

        if(reason==DSDP_CONVERGED)
        	mexPrintf("\n Final Primal Objective:  %2.5g\n Final Dual Objective:    %2.5g\n In %5d iterations\n    %5.2f seconds\n",*pval,*dval,iters,evaltime);

        mexPrintf("------------------------------------------------------------------\n\n");
    }  

    //Free DSDP Problem
    DSDP_ERR( DSDPDestroy(dsdp), "Error Destroying DSDP Problem");
    //Free Temporary memory
    if(temp_jc)  {mxFree(temp_jc);  temp_jc  = NULL;}
    if(temp_ir)  {mxFree(temp_ir);  temp_ir  = NULL;}
    if(temp_pr)  {mxFree(temp_pr);  temp_pr  = NULL;}
}               
Пример #24
0
// Function definitions. 
// -----------------------------------------------------------------
void mexFunction (int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[]) 
{
    //Input Args         
    double *x0 = NULL, *lb = NULL, *ub = NULL, *A = NULL, *b = NULL;  
    
    //Outputs Args
    double *x, *fval, *exitflag, *iter, *feval;
    
    //Internal Vars
    double *llb, *lub;
    size_t ndec;   
    int i, exit_code;    
    
    //PSwarm Vars
    double *sol = NULL;
    int lincon = 0;

    if (nrhs < 1) {
        if(nlhs < 1)
            printSolverInfo();
        else
            plhs[0] = mxCreateString(PSWARM_VERSION);
        return;
    }
    
    //Check user inputs
    checkInputs(prhs,nrhs,&lincon);
    
    //Set Defaults    
    printLevel = 0;
    maxtime = 1000;
    noFeval = 0;
    ctrlCExit = false;
    iterF.enabled = false;
    //Reset Stats
    stats.solveriters = 0;
    stats.objfunctions = 0;
    stats.pollsteps = 0;
    stats.sucpollsteps = 0;
    //Set PSwarm Defaults
    opt.s = 42;
    opt.mu = 0.5; opt.nu = 0.5;
    opt.maxvfactor = 0.5; opt.maxiter = 1500;
    opt.maxf = 10000;       
    opt.iweight = 0.9; opt.fweight = 0.4;
    opt.n2grd = 0.5;
    opt.blim = 10;
    opt.tol = 1e-5;
    opt.delta = Inf; opt.fdelta = 5.0; opt.idelta = 2.0; opt.ddelta = 0.5;
    opt.pollbasis = 0; opt.EpsilonActive = 0.1;
    opt.IPrint = 10;    
    opt.vectorized = 0;     //important, otherwise will pass whole swarm
    opt.outfcn = &iterfcn;  //iteration + ctrl c

    //Get Sizes
    ndec = mxGetNumberOfElements(prhs[1]);
    //Get Objective Function Handle
    if (mxIsChar(prhs[0])) {
        CHECK(mxGetString(prhs[0], fun.f, FLEN) == 0,"error reading objective name string");
        fun.nrhs = 1;
        fun.xrhs = 0;
    } else {
        fun.prhs[0] = (mxArray*)prhs[0];
        strcpy(fun.f, "feval");
        fun.nrhs = 2;
        fun.xrhs = 1;
    }    

    //Get x0
    x0 = mxGetPr(prhs[1]);   
    
    //Get Bounds
    //LB
    if(!mxIsEmpty(prhs[2])){
        llb = mxGetPr(prhs[2]);
        lb = mxCalloc(ndec,sizeof(double));
        memcpy(lb,llb,ndec*sizeof(double));
        for(i=0;i<ndec;i++) {
            if(mxIsInf(lb[i]))
                lb[i] = -1e19;
        }
    }
    else {
        lb = mxCalloc(ndec,sizeof(double));
        for(i=0;i<ndec;i++)
            lb[i] = -1e19;
    }
    //UB
    if(nrhs > 3 && !mxIsEmpty(prhs[3])){
        lub = mxGetPr(prhs[3]);
        ub = mxCalloc(ndec,sizeof(double));
        memcpy(ub,lub,ndec*sizeof(double));
        for(i=0;i<ndec;i++) {
            if(mxIsInf(ub[i]))
                ub[i] = 1e19;
        }
    }
    else {
        ub = mxCalloc(ndec,sizeof(double));
        for(i=0;i<ndec;i++)
            ub[i] = 1e19;
    }
    
    //Get Linear Inequality Constraints
    if(nrhs > 4) {
        if(!mxIsEmpty(prhs[4]) && !mxIsEmpty(prhs[5])) {
            A = mxGetPr(prhs[4]);
            b = mxGetPr(prhs[5]);
        }
    }
    
    //Get Options if specified
    if(nrhs > 6) {
        if(mxGetField(prhs[6],0,"display"))
            printLevel = (int)*mxGetPr(mxGetField(prhs[6],0,"display"));
        if(mxGetField(prhs[6],0,"maxiter"))
            opt.maxiter = (int)*mxGetPr(mxGetField(prhs[6],0,"maxiter"));
        if(mxGetField(prhs[6],0,"maxtime"))
            maxtime = *mxGetPr(mxGetField(prhs[6],0,"maxtime"));
        if(mxGetField(prhs[6],0,"tolfun"))
            opt.tol = *mxGetPr(mxGetField(prhs[6],0,"tolfun"));
        if(mxGetField(prhs[6],0,"maxfeval"))
            opt.maxf = (int)*mxGetPr(mxGetField(prhs[6],0,"maxfeval"));
        if(mxGetField(prhs[6],0,"swarm_size"))
            opt.s = (int)*mxGetPr(mxGetField(prhs[6],0,"swarm_size"));
        if(mxGetField(prhs[6],0,"vectorized"))
            opt.vectorized = (int)*mxGetPr(mxGetField(prhs[6],0,"vectorized"));
        if(mxGetField(prhs[6],0,"mu"))
            opt.mu = *mxGetPr(mxGetField(prhs[6],0,"mu"));
        if(mxGetField(prhs[6],0,"nu"))
            opt.nu = *mxGetPr(mxGetField(prhs[6],0,"nu"));
        if(mxGetField(prhs[6],0,"iweight"))
            opt.iweight = *mxGetPr(mxGetField(prhs[6],0,"iweight"));
        if(mxGetField(prhs[6],0,"fweight"))
            opt.fweight = *mxGetPr(mxGetField(prhs[6],0,"fweight"));
        if(mxGetField(prhs[6],0,"delta"))
            opt.delta = *mxGetPr(mxGetField(prhs[6],0,"delta"));
        if(mxGetField(prhs[6],0,"idelta"))
            opt.idelta = *mxGetPr(mxGetField(prhs[6],0,"idelta"));
        if(mxGetField(prhs[6],0,"ddelta"))
            opt.ddelta = *mxGetPr(mxGetField(prhs[6],0,"ddelta"));
        if(mxGetField(prhs[6],0,"iterfun") && !mxIsEmpty(mxGetField(prhs[6],0,"iterfun")))
        {
            iterF.prhs[0] = (mxArray*)mxGetField(prhs[6],0,"iterfun");
            strcpy(iterF.f, "feval");
            iterF.enabled = true;  
            iterF.prhs[1] = mxCreateNumericMatrix(1,1,mxINT32_CLASS,mxREAL);
            iterF.prhs[2] = mxCreateDoubleMatrix(1,1,mxREAL);
            iterF.prhs[3] = mxCreateDoubleMatrix(ndec,1,mxREAL);
        }
    }       
    
    //If not vectorized, we can create x now, otherwise must be done in callback
    if(!opt.vectorized)
        fun.prhs[fun.xrhs] = mxCreateDoubleMatrix(ndec, 1, mxREAL);
    
    //Create Outputs
    plhs[0] = mxCreateDoubleMatrix(ndec,1, mxREAL);
    plhs[1] = mxCreateDoubleMatrix(1,1, mxREAL);
    plhs[2] = mxCreateDoubleMatrix(1,1, mxREAL);
    plhs[3] = mxCreateDoubleMatrix(1,1, mxREAL);
    plhs[4] = mxCreateDoubleMatrix(1,1, mxREAL);
    x = mxGetPr(plhs[0]); 
    fval = mxGetPr(plhs[1]); 
    exitflag = mxGetPr(plhs[2]);    
    iter = mxGetPr(plhs[3]);
    feval = mxGetPr(plhs[4]);

    //Print Header
    if(printLevel) {
        mexPrintf("\n------------------------------------------------------------------\n");
        mexPrintf(" This is PSwarm v1.5\n");
            
        mexPrintf(" Authors: A.I.F Vaz and L.N. Vicente\n\n");
        mexPrintf(" Problem Properties:\n");
        mexPrintf(" # Decision Variables:     %4d\n",ndec);
        mexPrintf(" # Linear Constraints:     %4d\n",lincon);

        mexPrintf("------------------------------------------------------------------\n");
    }
    
    //Run PSwarm
    start = clock();
    exit_code = PSwarm((int)ndec, &func, lb, ub, lincon, A, b, &sol, fval, x0);
    
    if(exit_code == 0) {
        //Copy Solution
        memcpy(x,sol,ndec*sizeof(double));
        free(sol);
        *iter = (double)stats.solveriters;
        *feval = (double)stats.objfunctions;
    }

    //Save Status & Iterations
    *exitflag = getStatus(exit_code,stats.solveriters,stats.objfunctions); 
    
    //Print Header
    if(printLevel){            
        //Termination Detected
        switch((int)*exitflag)
        {
            //Success
            case 1:
                mexPrintf("\n *** SUCCESSFUL TERMINATION ***\n *** Normal Exit ***\n"); break;
            //Error
            case -1:
                mexPrintf("\n *** ERROR: Abnormal Exit ***\n"); break;
            case 0:
                if(stats.solveriters >= (opt.maxiter-5))
                    mexPrintf("\n *** MAXIMUM ITERATIONS REACHED ***\n"); 
                else if(((double)(end-start))/CLOCKS_PER_SEC > maxtime)
                    mexPrintf("\n *** MAXIMUM TIME EXCEEDED ***\n");
                else
                    mexPrintf("\n *** MAXIMUM FUNCTION EVALUATIONS REACHED ***\n"); 
                
                break;
            //Early Exit
            case -2:
                mexPrintf("\n *** TERMINATION: EARLY EXIT ***\n *** CAUSE: Failed to allocate memory ***\n"); break;
            case -3:
                mexPrintf("\n *** TERMINATION: EARLY EXIT ***\n *** CAUSE: Unable to initialize population - check constraints are feasible ***\n"); break;
            case -5:
                mexPrintf("\n *** TERMINATION: EARLY EXIT ***\n *** CAUSE: User Exit (Ctrl C) ***\n"); break;
        }

        if(*exitflag==1)
            mexPrintf("\n Final Objective: %12.5g\n In %3d iterations and\n   %4d function evaluations\n",*fval,stats.solveriters,stats.objfunctions);

        mexPrintf("------------------------------------------------------------------\n\n");
    }
    
    //Free Memory
    if(lb) mxFree(lb);
    if(ub) mxFree(ub);    
}
Пример #25
0
/* here comes the main function */
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
    /* default settings */
    /* connectivity pattern: 2 */
    const double DEF_clconn = 2.0;

    /* threshold 1 (consider also single voxel clusters) */
    const double DEF_kthr   = 1.0;

    /* setting pointers (for argument read-out) */
    const double *clconn = NULL;
    const double *kthr   = NULL;

    /* settings (internal) */
    /* max directions */
    unsigned int md = 2;

    /* cluster threshold */
    unsigned int kthrl = 1;



    /* sizes and position */
    const int *dim = NULL;
    int idim[3] = {1, 1, 1};
    int tdim[3] = {1, 1, 1};

    /* offset (must be variable, as copy might not require additional slices) */
    unsigned int toff[3] = {1, 1, 1};

    /* dimX, dimY, dimZ, dimXY, next position */
    unsigned int dx = 0, dy = 0, dz = 0, dxy = 0, dxyz = 0, np = 0;

    /* data pointers */
    /* (enlarged) copy */
    unsigned char *copy = NULL;

    /* list of cluster voxels */
    unsigned int clvoxcnt;
    unsigned int clnxtvox;
    signed int *clvox = NULL;

    /* list of cluster sizes and total number of clustered voxels */
    unsigned int mxclnum = 0;
    unsigned int clnum = 0;
    unsigned int *clsiz = NULL;
    unsigned int cltvox = 0, cltvox2 = 0, cltvox3 = 0;

    /* clustered volume (internal) */
    unsigned int *clvol = NULL;

    /* direction increments (as index differences) */
    signed int dlxyz[26] =
        {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};

    /* next positions (signed!) */
    signed int nextp = 0, nextpi = 0;

    /* counters */
    signed char dc = 0;
    unsigned int cx = 0, cy = 0, cz = 0;

    /* output pointer(s) */
    mxArray *ma = NULL;
    double *op = NULL, *sop = NULL;

    /* variable output text */
    /* char vstr[256]; */



    /* code starts here */



    /* nr. of arguments check */
    if ((nrhs < 1) ||
        (nlhs > 4))
        mexErrMsgTxt("Bad number of input/output arguments.");

    /* first argument class and size check */
    if (!mxIsLogical(prhs[0]) ||
        (mxGetNumberOfElements(prhs[0]) < 8) ||
        (mxGetNumberOfDimensions(prhs[0]) > 3))
        mexErrMsgTxt("Invalid argument type or dimension.");

    /* check connectivity flag */
    if ((nrhs < 2) ||
        !mxIsDouble(prhs[1]) ||
        (mxGetNumberOfElements(prhs[1]) != 1))
	clconn = &DEF_clconn;
    else {
	clconn = (const double*) mxGetPr(prhs[1]);
	if (mxIsNaN(*clconn) ||
	    mxIsInf(*clconn) ||
	   ((*clconn) < 1.0) ||
	   ((*clconn) > 5.0))
	    clconn = &DEF_clconn;
    }

    /* check threshold */
    if ((nrhs < 3) ||
        !mxIsDouble(prhs[2]) ||
        (mxGetNumberOfElements(prhs[2]) != 1))
        kthr = &DEF_kthr;
    else {
        kthr = (const double*) mxGetPr(prhs[2]);
        if (mxIsNaN(*kthr) ||
            mxIsInf(*kthr) ||
           ((*kthr) < 1.0) ||
           ((*kthr) > (0.5 * mxGetNumberOfElements(prhs[0]))))
            kthr = &DEF_kthr;
    }
    kthrl = (unsigned int) *kthr;

    /* get & check argument content */
    dim = mxGetDimensions(prhs[0]);
    idim[0] = dim[0];
    idim[1] = dim[1];
    if (mxGetNumberOfDimensions(prhs[0]) > 2)
        idim[2] = dim[2];
    dx = idim[0];
    dy = idim[1];
    dz = idim[2];
    dxy = dx * dy;
    dxyz = dxy * dz;
    mxclnum = (unsigned int) (((double) (dxyz + 3)) / 4.0);

    /* set connectivity flag -> max directions (opposite direction later) */
    /* face connectivity -> three main directions */
    if ((*clconn >= 1.0) && (*clconn < 1.5))
        md = 3;

    /* edge connectivity -> add 6 edge diagonals */
    else if ((*clconn >= 1.5) && (*clconn < 2.5))
        md = 9;

    /* vertex connectivity -> add 4 3D diagonals */
    else if ((*clconn >= 2.5) && (*clconn < 3.5))
        md = 13;
    /* otherwise, leave at 2, we stay "in-plane" */

    /* reserve space for next cluster list and cluster sizes */
    clvox = (signed int *) mxCalloc(dxyz, sizeof(signed int));
    if (clvox == NULL)
	mexErrMsgTxt("Error allocating next cluster voxel list.");
    clsiz = (unsigned int *) mxCalloc(mxclnum, sizeof(signed int));
    if (clsiz == NULL) {
        mxFree(clvox);
	mexErrMsgTxt("Error allocating next cluster voxel list.");
    }

    /* increase numbers accordingly */
    if (idim[0] > 1)
        dx += 2;
    else
        toff[0] = 0;
    if (idim[1] > 1)
        dy += 2;
    else
        toff[1] = 0;
    if (idim[2] > 1)
        dz += 2;
    else
        toff[2] = 0;

    /* compute new plane/vol numel */
    dxy = dx * dy;
    dxyz = dxy * dz;

    /* reserve space for clustered volume (if needed) */
    if (nlhs > 1) {
        clvol = (unsigned int *) mxCalloc(dxyz, sizeof(unsigned int));
        if (clvol == NULL) {
            mxFree(clsiz);
            mxFree(clvox);
            mexErrMsgTxt("Error allocating clustered volume.");
        }
    }

    /* set temp dim array */
    tdim[0] = dx;
    tdim[1] = dy;
    tdim[2] = dz;

    /* fill direction increment array */
    np = 0;
    for (dc = 0; dc < md; ++dc) {
        if (((idim[0] > 1) ||
             (dlx[dc] == 0)) &&
            ((idim[1] > 1) ||
             (dly[dc] == 0)) &&
            (((idim[2] > 1) &&
	      (*clconn < 3.5)) ||
             (dlz[dc] == 0))) {
            dlxyz[np] = dlx[dc] + dly[dc] * dx + dlz[dc] * dxy;
            dlxyz[np+1] = -dlxyz[np];
            np += 2;
        }
    }
    if ((*clconn >= 4.5) &&
        (idim[0] > 1) &&
        (idim[1] > 1)) {
        for (dc = 3; dc < 5; ++dc) {
            dlxyz[np] = dlx[dc] + dly[dc] * dx + dlz[dc] * dxy;
            dlxyz[np+1] = -dlxyz[np];
            np += 2;
        }
    }

    /* re-set */
    md = np - 1;

    /* create temp. copy array */
    copy = (unsigned char *) mxCalloc(dxyz, sizeof(unsigned char));
    if (copy == NULL) {
        mxFree(clsiz);
        mxFree(clvox);
        mexErrMsgTxt("Error allocating temporary memory");
    }

    /* copy into temporary array */
    ff_copy_intopart(idim[0], idim[1], idim[2], (unsigned char *) mxGetPr(prhs[0]), tdim, copy, toff);



    /* preparations complete, now we can "search"... */



    /* iterate while new points found */
    for (np = 0; np < dxyz; ++np) {

	/* check voxel */
        if (copy[np] == 1) {

            /* start new cluster */
            clvoxcnt = 1;
            clvox[0] = np;

            /* remove from search volume */
            copy[np] = 0;

            /* continue until no more neighbors found */
            for (clnxtvox = 0; clnxtvox < clvoxcnt; ++clnxtvox) {

                /* check neighbors */
                nextp = clvox[clnxtvox];
                for (dc = md;  dc >= 0; --dc) {

                    /* check voxel with increment */
                    nextpi = nextp + dlxyz[dc];
                    if (copy[nextpi] == 1) {

                            /* equally remove from search volume */
                            copy[nextpi] = 0;

                            /* and add to list */
                            clvox[clvoxcnt++] = nextpi;
                    }
                }
            }

            /* rest of code only if surpasses threshold */
            if (clvoxcnt >= kthrl) {

                /* write to list of sizes and increase cluster number count */
                clsiz[clnum++] = clvoxcnt;
                cltvox += clvoxcnt;

                /* write to output volume (if needed) */
                if (nlhs > 1) {
                    for (nextp = clvoxcnt - 1; nextp >= 0; --nextp)
                        clvol[clvox[nextp]] = clnum;
                }
            }
        }
    }

    /* we're done with this */
    mxFree(copy);

    /* create output argument #1 */
    CREATE_MxN(plhs[0], 1, clnum);
    if (plhs[0] == NULL) {
        if (clvol != NULL)
            mxFree(clvol);
        mxFree(clsiz);
        mxFree(clvox);
        mexErrMsgTxt("Error creating output argument cs.");
    }

    /* if requested create other outputs first */
    if (nlhs > 1) {
        plhs[1] = mxCreateNumericArray(3, idim, mxUINT32_CLASS, mxREAL);
        if (plhs[1] == NULL) {
            mxDestroyArray(plhs[0]);
            mxFree(clvol);
            mxFree(clsiz);
            mxFree(clvox);
            mexErrMsgTxt("Error creating output argument cv.");
        }
    }

    /* if requested create other outputs first */
    if (nlhs > 2) {
        CREATE_MxN(plhs[2], cltvox, 4);
        if (plhs[2] == NULL) {
            mxDestroyArray(plhs[1]);
            mxDestroyArray(plhs[0]);
            mxFree(clvol);
            mxFree(clsiz);
            mxFree(clvox);
            mexErrMsgTxt("Error creating output argument l.");
        }
    }

    /* if requested create other outputs first */
    if (nlhs > 3) {
        plhs[3] = mxCreateCellMatrix(1, clnum);
        if (plhs[3] == NULL) {
            mxDestroyArray(plhs[2]);
            mxDestroyArray(plhs[1]);
            mxDestroyArray(plhs[0]);
            mxFree(clvol);
            mxFree(clsiz);
            mxFree(clvox);
            mexErrMsgTxt("Error creating output argument c.");
        }
        /* put numeric array into each cell */
        for (nextp = 0; nextp < clnum; ++nextp) {
            CREATE_MxN(ma, clsiz[nextp], 3);
            if (ma == NULL) {
                mxDestroyArray(plhs[3]);
                mxDestroyArray(plhs[2]);
                mxDestroyArray(plhs[1]);
                mxDestroyArray(plhs[0]);
                mxFree(clvol);
                mxFree(clsiz);
                mxFree(clvox);
                mexErrMsgTxt("Error creating output cell contents in argument c.");
            }
            mxSetCell(plhs[3], nextp, ma);
        }
    }

    /* copy cluster sizes into output */
    op = (double *) mxGetPr(plhs[0]);
    for (nextp = 0; nextp < clnum; ++nextp)
        *op++ = (double) clsiz[nextp];

    /* copy volume to output */
    if (nlhs > 1) {
        ff_copy_frompart(dx, dy, clvol, idim, (unsigned int*) mxGetData(plhs[1]), toff);
        mxFree(clvol);
        clvol = (unsigned int *) mxGetPr(plhs[1]);
    }

    /* create list of voxels */
    if (nlhs > 2) {

        /* get output pointer */
        op = (double *) mxGetPr(plhs[2]);

        /* 2/3 * total count for fast indexing */
        cltvox2 = 2 * cltvox;
        cltvox3 = 3 * cltvox;

        /* if required re-init counter */
        if (nlhs > 3) {
            for (nextp = clnum - 1; nextp >= 0; --nextp)
                clvox[nextp] = 0;
        }

        dx = idim[0];
        dy = idim[1];
        dz = idim[2];
        dxy = dx * dy;
        for (cz = 0; cz < dz; ++cz) {
            dxyz = dxy * cz;
            for (cy = 0; cy < dy; ++cy) {
                np = dxyz + cy * dx;
                for (cx = 0; cx < dx; ++cx) {
                    clnum = *clvol++;
                    if (clnum > 0) {
                        op[cltvox3] = (double) clnum;
                        op[cltvox2] = (double) (cz + 1);
                        op[cltvox]  = (double) (cy + 1);
                        *op++ = (double) (cx + 1);
                        if (nlhs > 3) {
                            --clnum;
                            sop = (double *) mxGetPr(mxGetCell(plhs[3], clnum));
                            sop[2 * clsiz[clnum] + clvox[clnum]] = (double) (cz + 1);
                            sop[clsiz[clnum] + clvox[clnum]] = (double) (cy + 1);
                            sop[clvox[clnum]++] = (double) (cx + 1);
                        }
                    }
                }
            }
        }
    }

    /* free other temp arrays */
    mxFree(clsiz);
    mxFree(clvox);

}
Пример #26
0
// [outputData, sampsPerChanRead] = readAnalogData(task, numSampsPerChan, outputFormat, timeout, outputVarSizeOrName)
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
	//Read input arguments

	// Get the task handle
	mxArray *mxTaskID = mxGetProperty(prhs[0],0,"taskID");
	mxClassID clsID = mxGetClassID(mxTaskID);
	localAssert(clsID==TASKHANDLE_MXCLASS);
	TaskHandle *taskIDPtr = (TaskHandle*)mxGetData(mxTaskID);
	TaskHandle taskID = *taskIDPtr;

	//Determine if this is a buffered read operation
	uInt32 bufSize = 0;
	int32 status = DAQmxGetBufInputBufSize(taskID,&bufSize);
	if (status) {
		handleDAQmxError(status,"DAQmxGetBufInputBufSize");
	}

	// Handle input arguments

	int32 numSampsPerChan = 0; // this does take negative vals in the case of DAQmx_Val_Auto
	if ((nrhs < 2) || mxIsEmpty(prhs[1]) || mxIsInf(mxGetScalar(prhs[1]))) {
		if (bufSize==0)
			numSampsPerChan = 1;
		else
			numSampsPerChan = DAQmx_Val_Auto;
	} else {
		numSampsPerChan = (int) mxGetScalar(prhs[1]);
	}
	
	char outputFormat[10];
	if ((nrhs < 3) || mxIsEmpty(prhs[2]))
		strcpy_s(outputFormat,"scaled");
	else
		mxGetString(prhs[2], outputFormat, 10);

	double timeout;
	if ((nrhs < 4) || mxIsEmpty(prhs[3]) || mxIsInf(mxGetScalar(prhs[3])))
		timeout = DAQmx_Val_WaitInfinitely;
	else
		timeout = mxGetScalar(prhs[3]);

	bool outputData; //Indicates whether to return an outputData argument
	int outputVarSampsPerChan = 0; // this CAN take negative values in case of DAQmx_Val_Auto
	char outputVarName[MAXVARNAMESIZE];	
	if ((nrhs < 5) || mxIsEmpty(prhs[4])) {
		outputData = true;
		outputVarSampsPerChan = numSampsPerChan; //If value is DAQmx_Val_Auto, then the # of samples available will be queried before allocting array
	} else {
		outputData = mxIsNumeric(prhs[4]);
		if (outputData) {
			if (nlhs < 2) {
				mexErrMsgTxt("There must be two output arguments specified if a preallocated MATLAB variable is not specified");
			}
			outputVarSampsPerChan = (int) mxGetScalar(prhs[4]);
		} else {
			mxGetString(prhs[4],outputVarName,MAXVARNAMESIZE);
		}
	}

	//Determine output data type
	mxClassID outputDataClass;
	mxArray *mxRawDataArrayAI = mxGetProperty(prhs[0],0,"rawDataArrayAI"); //Stored in MCOS Task object as an empty array of the desired class!
	mxClassID rawDataClass = mxGetClassID(mxRawDataArrayAI); 

	char errorMessage[30];
	if (!_strcmpi(outputFormat,"scaled"))
		outputDataClass = mxDOUBLE_CLASS;
	else if (!_strcmpi(outputFormat,"native"))
		outputDataClass = rawDataClass;
	else {
		sprintf_s(errorMessage,"Unrecognized output format: %s\n",outputFormat);
		mexErrMsgTxt(errorMessage);
	}		

	//Determine # of output channels
	uInt32 numChannels; 
	DAQmxGetReadNumChans(taskID,&numChannels); //Reflects number of channels in Task, or the number of channels specified by 'ReadChannelsToRead' property
	
	//Determine output buffer/size (creating if needed)
	mxArray *mxOutputDataBuf = NULL;
	if (outputData)	{
		if (outputVarSampsPerChan == DAQmx_Val_Auto) {
			uInt32 buf = 0;
			status = DAQmxGetReadAvailSampPerChan(taskID,&buf);
			if (status) {
				handleDAQmxError(status, mexFunctionName());
			}
			outputVarSampsPerChan = buf;
		}

		//localAssert(outputVarSampsPerChan >= 0);
		localAssert(outputVarSampsPerChan > 0);
		mxOutputDataBuf = mxCreateNumericMatrix(outputVarSampsPerChan,numChannels,outputDataClass,mxREAL);
	} else {
		localAssert(false);
		////I don't believe this is working
		//mxOutputDataBuf = mexGetVariable("caller", outputVarName);
		//outputVarSampsPerChan = mxGetM(mxOutputDataBuf);
		////TODO: Add check to ensure WS variable is of correct class
	}

	void* outputDataPtr = mxGetData(mxOutputDataBuf);
	localAssert(outputDataPtr!=NULL);

	uInt32 arraySizeInSamps = outputVarSampsPerChan * numChannels;
	localAssert(mxGetNumberOfElements(mxOutputDataBuf)==(size_t)arraySizeInSamps);
	int32 numSampsPerChanRead;

	
	if (outputDataClass == mxDOUBLE_CLASS) //'scaled' 
		// float64 should be double
		status = DAQmxReadAnalogF64(taskID,numSampsPerChan,timeout,fillMode,
				(float64*) outputDataPtr, arraySizeInSamps, &numSampsPerChanRead, NULL);
	else { //'raw'
		switch (outputDataClass)
		{
			case mxINT16_CLASS:
				status = DAQmxReadBinaryI16(taskID, numSampsPerChan, timeout, fillMode, (int16*) outputDataPtr, arraySizeInSamps, &numSampsPerChanRead, NULL);
				break;
			case mxINT32_CLASS:
				status = DAQmxReadBinaryI32(taskID, numSampsPerChan, timeout, fillMode, (int32*) outputDataPtr, arraySizeInSamps, &numSampsPerChanRead, NULL);
				break;
			case mxUINT16_CLASS:
				status = DAQmxReadBinaryU16(taskID, numSampsPerChan, timeout, fillMode, (uInt16*) outputDataPtr, arraySizeInSamps, &numSampsPerChanRead, NULL);
				break;
			case mxUINT32_CLASS:
				status = DAQmxReadBinaryU32(taskID, numSampsPerChan, timeout, fillMode, (uInt32*) outputDataPtr, arraySizeInSamps, &numSampsPerChanRead, NULL);
				break;
		}
	}

	//Return output data
	if (!status)
	{
		//mexPrintf("Successfully read %d samples of data\n", numSampsRead);

		if (outputData) {
			if (nlhs > 0)
				plhs[0] = mxOutputDataBuf;
			else				
				mxDestroyArray(mxOutputDataBuf); //If you don't read out, all the reading was done for naught
		} else {
			//I don't believe this is working
			localAssert(false);
			//mexPutVariable("caller", outputVarName, mxOutputDataBuf);
			//
			//if (nlhs >= 0) //Return empty value for output data
			//	plhs[0] = mxCreateDoubleMatrix(0,0,mxREAL);
		}
			

		if (nlhs>1) { //Return number of samples actually read
			plhs[1] = mxCreateDoubleScalar(0.0);	
			double *sampsReadOutput = mxGetPr(plhs[1]);
			*sampsReadOutput = (double)numSampsPerChanRead;
		}
	} else { //Read failed
		handleDAQmxError(status, mexFunctionName());
	}

}
Пример #27
0
/* -------------------------------------------------------------------
 Main MEX function - interface to Matlab.
-------------------------------------------------------------------- */
void mexFunction( int nlhs, mxArray *plhs[],int nrhs, const mxArray*prhs[] )
{
  char solver[20];   /* solver identifier */
  int exitflag;      /* output arg */
  int buf_len;       /* real length of the solver identifier */
  int verb;          /* input argument -- verbosity */
  long i ;           /* loop variable */
  long tmax;         /* input arg - max number of iteration */ 
  long t;            /* output arg - number of iterations */
  double tolrel;     /* input arg */
  double tolabs;     /* input arg */
  double tolKKT;     /* input arg */
  double *tmp_ptr;  
  double *x;         /* output arg -- solution*/ 
  double *History;   /* output arg */
  double *diag_H;    /* diagonal of matrix H */
  double *f;         /* vector f */
  
  /*------------------------------------------------------------------- */
  /* Take input arguments                                               */
  /*------------------------------------------------------------------- */

  if( nrhs != 8) mexErrMsgTxt("Incorrect number of input arguments.");

  /* matrix H */
  matrix_H = mxGetPr(prhs[0]);   
  dim = mxGetM(prhs[0]);     

  if(dim != mxGetN(prhs[0])) mexErrMsgTxt("Matrix H mast be squared.");
   
  /* vector f */
  f = mxGetPr(prhs[1]);   
  if((MAX(mxGetM(prhs[1]),mxGetN(prhs[1])) != dim) ||
     (MIN(mxGetM(prhs[1]),mxGetN(prhs[1])) != 1))
      mexErrMsgTxt("Vector f is of wrong size.");

  /* string identifier of QP solver to be used */
  if( mxIsChar( prhs[2] ) != 1) mexErrMsgTxt("Solver must be a string.");
  buf_len = (mxGetM(prhs[2]) * mxGetN(prhs[2])) + 1;
  buf_len = (buf_len > 20) ? 20 : buf_len;
  mxGetString( prhs[2], solver, buf_len );

  /* maximal allowed number of iterations */
  tmax = mxIsInf( mxGetScalar(prhs[3])) ? INT_MAX : (long)mxGetScalar(prhs[3]); 
  tolabs = mxGetScalar(prhs[4]);   /* abs. precision defining stopping cond*/
  tolrel = mxGetScalar(prhs[5]);   /* rel. precision defining stopping cond*/

  /* KKT cond. tolerance */
  tolKKT = (double)mxGetScalar(prhs[6]); 

  verb = (int)mxGetScalar(prhs[7]);  /* verbosity on/off */

  if( verb > 0 ) {
    mexPrintf("Settings of QP solver\n");
    mexPrintf("solver : %s\n", solver );
    mexPrintf("tmax   : %d\n", tmax );
    mexPrintf("tolabs : %f\n", tolabs );
    mexPrintf("tolrel : %f\n", tolrel );
    mexPrintf("tolKKT : %f\n", tolKKT );
    mexPrintf("dim    : %d\n", dim );
    mexPrintf("verb   : %d\n", verb );
  }

  /*------------------------------------------------------------------- */ 
  /* Inicialization                                                     */
  /*------------------------------------------------------------------- */

  /* output "solution" vector alpha [dim x 1] */
  plhs[0] = mxCreateDoubleMatrix(dim,1,mxREAL);
  x = mxGetPr(plhs[0]);

  /* allocattes and precomputes diagonal of virtual K matrix */
  diag_H = mxCalloc(dim, sizeof(double));
  if( diag_H == NULL ) mexErrMsgTxt("Not enough memory.");
  for(i = 0; i < dim; i++ ) {
    diag_H[i] = matrix_H[dim*i+i];
  }

  /* counter of access to matrix H */
  access = dim;

  /*------------------------------------------------------------------- */
  /* Call QP solver                                                     */
  /*------------------------------------------------------------------- */

  if ( strcmp( solver, "sca" ) == 0 ) {  
     exitflag = gnnls_sca( &get_col, diag_H, f, dim, tmax, 
         tolabs, tolrel, tolKKT, x, &t, &History, verb );
  } else   if ( strcmp( solver, "scas" ) == 0 ) {  
     exitflag = gnnls_scas( &get_col, diag_H, f, dim, tmax, 
         tolabs, tolrel, tolKKT, x, &t, &History, verb );
  } else {
     mexErrMsgTxt("Unknown QP solver identifier!");
  }

  /*------------------------------------------------------------------- */
  /* Generate outputs                                                   */
  /*------------------------------------------------------------------- */

  /* exitflag [1x1] */
  plhs[1] = mxCreateDoubleMatrix(1,1,mxREAL);
  *(mxGetPr(plhs[1])) = (double)exitflag;

  /* t [1x1] */
  plhs[2] = mxCreateDoubleMatrix(1,1,mxREAL);
  *(mxGetPr(plhs[2])) = (double)t;

  /* access [1x1] */
  plhs[3] = mxCreateDoubleMatrix(1,1,mxREAL);
  *(mxGetPr(plhs[3])) = (double)access;

  /* History [2 x (t+1)] */
  plhs[4] = mxCreateDoubleMatrix(2,t+1,mxREAL);
  tmp_ptr = mxGetPr( plhs[4] );
  for( i = 0; i <= t; i++ ) {
     tmp_ptr[INDEX(0,i,2)] = History[INDEX(0,i,2)];
     tmp_ptr[INDEX(1,i,2)] = History[INDEX(1,i,2)];
  }

  /*------------------------------------------------------------------- */
  /* Free used memory                                                   */
  /*------------------------------------------------------------------- */
  mxFree( History );
  mxFree( diag_H );
}
Пример #28
0
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{

  /* input parameters */
  double WidT, PosT;
  double *T, *Pos, *Wid, *Amp, *x;
  /* output parameters */
  double *y;
  /* working variables */
  long nT, nx, nPdat, nIdat, nWdat;
  long idx, first, last, k, idxT;
  double alpha, beta, delta, deltaT;
  double left, right, WidS, Amplitude, pT, remT, Value, ValueOld;
  bool Verbose, InfEncountered, NaNEncountered, NegEncountered;
  /*int Harmonic; */

  Verbose = false;

  /* Argument checks. */
  if (nrhs!=7) mexErrMsgTxt("Wrong number of input parameters!");
  if (nlhs!=1) mexErrMsgTxt("Wrong number of output parameters!");

  /* Get all input arguments. */
  T = mxGetPr(prhs[0]);
  PosT = mxGetScalar(prhs[1]) - 1; /* Matlab -> C array indices */
  WidT = mxGetScalar(prhs[2]);
  Pos = mxGetPr(prhs[3]);
  Amp = mxGetPr(prhs[4]);
  Wid = mxGetPr(prhs[5]);
  x = mxGetPr(prhs[6]);
  /*Harmonic = 0;*/

  /* Get vector lengths. */
  nPdat = mxGetNumberOfElements(prhs[3]);
  nIdat = mxGetNumberOfElements(prhs[4]);
  nWdat = mxGetNumberOfElements(prhs[5]);

  if ((nPdat!=nIdat)||(nPdat!=nWdat))
    mexErrMsgTxt("Pos, Amp, Wid must have the same number of elements!");
  
  nT = mxGetNumberOfElements(prhs[0]);
  nx = mxGetNumberOfElements(prhs[6]);

  /* Allocate result array. */
  plhs[0] = mxCreateDoubleMatrix(1,nx,mxREAL);
  y = mxGetPr(plhs[0]);

  delta = x[1]-x[0];
  deltaT = 1;
  beta = delta/deltaT;

  /*if (Verbose) mexPrintf("begin of lisum1ic loop\n"); */
  /* Loop over all peaks to add. */
  InfEncountered = false;
  NaNEncountered = false;
  NegEncountered = false;
  for (k=0; k<nPdat; k++) {

    /* Skip if NaN or inf. */
    if (mxIsNaN(Pos[k])||mxIsNaN(Amp[k])||mxIsNaN(Wid[k])) {NaNEncountered=true; continue;}
    if (mxIsInf(Pos[k])||mxIsInf(Amp[k])||mxIsInf(Wid[k])) {InfEncountered=true; continue;}
    
    /* Set to zero if negative width */
    WidS = Wid[k];
    if (WidS<0) {NegEncountered=true; WidS=0;}
    
    /* If width is zero, set it to a small value */
    if (WidS<delta/100) WidS = delta/100;

    /* Scaling factor between template and spectrum abscissae */
    alpha = WidT/WidS * beta;
    
    /* Left and right border of line in spectrum. */
    left = (Pos[k]-x[0])/delta - PosT/alpha;
    left -= 0.5; /* Integration */
    right = left + (nT-1)/alpha;

    /* Skip peak if completely outside. */
    if ((left>=nx-1)||(right<=0)) continue; 

    /* Chop if necessary. */
    first = (long)((left<0) ? 0 : ceil(left));
    last = (long)((right>nx-1) ? nx-1 : ceil(right));

    /* scaled amplitude */
    Amplitude = Amp[k]/beta;
    /*if (Harmonic>0) { */
    /*  Amplitude *= WidT/WidS; */
    /*  if (Harmonic>1) Amplitude *= WidT/WidS; */
    /*} */
    /*if (Verbose) */
    /*  mexPrintf("  setup> left %g  right %g   first %d  last %d    A %g\n",left,right,first,last,Amplitude); */

    /* Loop over all points in spectrum to update. */
    pT = alpha*(first-left);
    idxT = (long)(pT-alpha);
    remT = pT - alpha - idxT;
    ValueOld = (idxT<0) ? T[0] : (T[idxT]*(1-remT) + T[idxT+1]*remT);
    /*if (Verbose) mexPrintf("    start: pT %5f    %11e ...\n",pT-alpha,ValueOld); */
    
    for (idx=first; idx<last; idx++, pT+=alpha, ValueOld=Value) {
      idxT = (long)pT;
      remT = pT - idxT;
      Value = T[idxT]*(1-remT) + T[idxT+1]*remT;
      /*if (Verbose) */
      /*  mexPrintf("    idxS %4d  pT %5f    %11e - %-11e...",idx,pT,Value,ValueOld); */
      y[idx] += Amplitude*(Value-ValueOld);
      /*if (Verbose) mexPrintf("added\n"); */
    }
    idxT = (long)pT;
    remT = pT - idxT;
    Value = idxT<nT-2 ? T[idxT]*(1-remT) + T[idxT+1]*remT : T[nT-1];
    /*if (Verbose) */
    /*    mexPrintf("  L:idxS %4d  pT %5f    %11e - %-11e...",idx,pT,Value,ValueOld); */
    y[idx] += Amplitude*(Value-ValueOld);
    /*if (Verbose) mexPrintf("added\n"); */
  } /* loop over all lines */
  /*if (Verbose) mexPrintf("end of lisum1ic loop\n"); */
  if (InfEncountered) mexPrintf("********** lisum1ic: Inf encountered!! Please report! **************\n");
  if (NegEncountered) mexPrintf("********** lisum1ic: Negative width encountered!! Please report! **************\n");
} /* void mexFunction */
Пример #29
0
void mexFunction( int nlhs, mxArray *plhs[],int nrhs, const mxArray *prhs[] )
{
  double C, TolRel, TolAbs, QPBound, trn_err, MaxTime;
  double *vec_C;   
  double *ptr;
  uint32_t num_of_Cs;
  uint32_t i, j, BufSize;
  uint16_t Method;
  int verb;
  ocas_return_value_T ocas;

  /* timing variables */
  double init_time;
  double total_time;

  total_time = get_time();
  init_time = total_time;

  if(nrhs < 1)
    mexErrMsgTxt("Improper number of input arguments.");

  /* get input arguments */ 
  if(mxIsChar(prhs[0]) == false) 
  {
    /* [W,W0,stat] = svmocas_mex(X,X0,y,C,Method,TolRel,TolAbs,QPBound,BufSize,nData,MaxTime); */

    if(nrhs < 4 || nrhs > 12)
      mexErrMsgTxt("Improper number of input arguments.");

    if(nrhs >= 12)
      verb = (int)mxGetScalar(prhs[11]);
    else
      verb = DEFAULT_VERB;


    data_X = (mxArray*)prhs[0];
    if (!(mxIsDouble(data_X)))
        mexErrMsgTxt("Input argument X must be of type double.");

    if (mxGetNumberOfDimensions(data_X) != 2)
        mexErrMsgTxt("Input argument X must be two dimensional");

    X0 = mxGetScalar(prhs[1]);
    data_y = (double*)mxGetPr(prhs[2]);

    if(LIBOCAS_MAX(mxGetM(prhs[2]),mxGetN(prhs[2])) != mxGetN(prhs[0]))
      mexErrMsgTxt("Length of vector y must equl to the number of columns of matrix X.");

    nDim = mxGetM(prhs[0]);

    if(verb)
    {
      mexPrintf("Input data statistics:\n"
                "   # of examples  : %d\n"
                "   dimensionality : %d\n",
                mxGetN(data_X), nDim);
    
      if( mxIsSparse(data_X)== true ) 
        mexPrintf("   density        : %.2f%%\n",
                  100.0*(double)mxGetNzmax(data_X)/((double)nDim*(double)(mxGetN(data_X))));
      else
        mexPrintf("   density        : 100%% (full)\n");
    }


    num_of_Cs = LIBOCAS_MAX(mxGetN(prhs[3]),mxGetM(prhs[3]));
    if(num_of_Cs == 1)
    {
       C = (double)mxGetScalar(prhs[3]);
    }
    else
    {
       vec_C = (double*)mxGetPr(prhs[3]);
    }

    if(nrhs >= 5)
      Method = (uint32_t)mxGetScalar(prhs[4]);
    else
      Method = DEFAULT_METHOD;

    if(nrhs >= 6)
      TolRel = (double)mxGetScalar(prhs[5]);
    else
      TolRel = DEFAULT_TOLREL;

    if(nrhs >= 7)    
      TolAbs = (double)mxGetScalar(prhs[6]);
    else
      TolAbs = DEFAULT_TOLABS;

    if(nrhs >= 8)
      QPBound = (double)mxGetScalar(prhs[7]);
    else
      QPBound = DEFAULT_QPVALUE;

    if(nrhs >= 9)
      BufSize = (uint32_t)mxGetScalar(prhs[8]);
    else
      BufSize = DEFAULT_BUFSIZE;

    if(nrhs >= 10 && mxIsInf(mxGetScalar(prhs[9])) == false)
      nData = (uint32_t)mxGetScalar(prhs[9]);
    else
      nData = mxGetN(data_X);
      
    if(nData < 1 || nData > mxGetN(prhs[0])) 
      mexErrMsgTxt("Improper value of argument nData.");

    if(num_of_Cs > 1 && num_of_Cs < nData)
      mexErrMsgTxt("Length of the vector C less than the number of examples.");

    if(nrhs >= 11)
      MaxTime = (double)mxGetScalar(prhs[10]);
    else
      MaxTime = DEFAULT_MAXTIME;
  } 
  else
  {
    /* [W,W0,stat] = svmocas_mex(svmlight_data_file,X0,C,Method,TolRel,TolAbs,QPBound,BufSize,nData,MaxTime); */
    char *fname;
    int fname_len;

    if(nrhs < 3 || nrhs > 11)
      mexErrMsgTxt("Improper number of input arguments.");

    if(nrhs >= 11)
      verb = (int)mxGetScalar(prhs[10]);
    else
      verb = DEFAULT_VERB;

    if(!mxIsChar(prhs[0]))
      mexErrMsgTxt("First input argument must be of type string.");

    fname_len = mxGetNumberOfElements(prhs[0]) + 1;   
    fname = mxCalloc(fname_len, sizeof(char));    

    if (mxGetString(prhs[0], fname, fname_len) != 0)     
      mexErrMsgTxt("Could not convert first input argument to string.");

    if( load_svmlight_file(fname,verb) == -1 || data_X == NULL || data_y == NULL)
      mexErrMsgTxt("Cannot load input file.");

    nDim = mxGetM(data_X);
    X0 = mxGetScalar(prhs[1]);

/*    C = (double)mxGetScalar(prhs[2]);*/
    num_of_Cs = LIBOCAS_MAX(mxGetN(prhs[2]),mxGetM(prhs[2]));
    if(num_of_Cs == 1)
    {
       C = (double)mxGetScalar(prhs[2]);
    }
    else
    {
       vec_C = (double*)mxGetPr(prhs[2]);
    }

    if(verb)
      mexPrintf("Input data statistics:\n"
                "   # of examples  : %d\n"
                "   dimensionality : %d\n"
                "   density        : %.2f%%\n",
                mxGetN(data_X), nDim, 100.0*(double)mxGetNzmax(data_X)/((double)nDim*(double)(mxGetN(data_X))));
    
    if(nrhs >= 4)
      Method = (uint32_t)mxGetScalar(prhs[3]);
    else
      Method = DEFAULT_METHOD;

    if(nrhs >= 5)
      TolRel = (double)mxGetScalar(prhs[4]);
    else
      TolRel = DEFAULT_TOLREL;

    if(nrhs >= 6)
      TolAbs = (double)mxGetScalar(prhs[5]);
    else
      TolAbs = DEFAULT_TOLABS;

    if(nrhs >= 7)
      QPBound = (double)mxGetScalar(prhs[6]);
    else
      QPBound = DEFAULT_QPVALUE;

    if(nrhs >= 8)    
      BufSize = (uint32_t)mxGetScalar(prhs[7]);
    else
      BufSize = DEFAULT_BUFSIZE;

    if(nrhs >= 9 && mxIsInf(mxGetScalar(prhs[8])) == false) 
      nData = (uint32_t)mxGetScalar(prhs[8]);
    else
      nData = mxGetN(data_X);

    if(nData < 1 || nData > mxGetN(data_X)) 
      mexErrMsgTxt("Improper value of argument nData.");

    if(num_of_Cs > 1 && num_of_Cs < nData)
      mexErrMsgTxt("Length of the vector C less than the number of examples.");

    if(nrhs >= 10)
      MaxTime = (double)mxGetScalar(prhs[9]);
    else
      MaxTime = DEFAULT_MAXTIME;

  } 


  /*----------------------------------------------------------------
    Print setting
  -------------------------------------------------------------------*/
  if(verb)
  {
    mexPrintf("Setting:\n");

    if( num_of_Cs == 1)
      mexPrintf("   C              : %f\n", C);
    else
      mexPrintf("   C              : different for each example\n");

    mexPrintf("   bias           : %.0f\n"
              "   # of examples  : %d\n"
              "   solver         : %d\n"
              "   cache size     : %d\n"
              "   TolAbs         : %f\n"
              "   TolRel         : %f\n"
              "   QPValue        : %f\n"
              "   MaxTime        : %f [s]\n"
              "   verb           : %d\n",
              X0, nData, Method,BufSize,TolAbs,TolRel, QPBound, MaxTime, verb);
  }
  
  /* learned weight vector */
  plhs[0] = (mxArray*)mxCreateDoubleMatrix(nDim,1,mxREAL);
  W = (double*)mxGetPr(plhs[0]);
  if(W == NULL) mexErrMsgTxt("Not enough memory for vector W.");

  oldW = (double*)mxCalloc(nDim,sizeof(double));
  if(oldW == NULL) mexErrMsgTxt("Not enough memory for vector oldW.");

  W0 = 0;
  oldW0 = 0;

  A0 = mxCalloc(BufSize,sizeof(A0[0]));
  if(A0 == NULL) mexErrMsgTxt("Not enough memory for vector A0.");

  /* allocate buffer for computing cutting plane */
  new_a = (double*)mxCalloc(nDim,sizeof(double));
  if(new_a == NULL) 
    mexErrMsgTxt("Not enough memory for auxciliary cutting plane buffer new_a.");  


  if(num_of_Cs > 1)
  {
    for(i=0; i < nData; i++) 
      data_y[i] = data_y[i]*vec_C[i];
  }


  if( mxIsSparse(data_X)== true ) {

    /* for i=1:nData, X(:,i) = X(:,i)*y(i); end*/
    for(i=0; i < nData; i++) 
        mul_sparse_col(data_y[i], data_X, i);           
  

    /* init cutting plane buffer */
    sparse_A.nz_dims = mxCalloc(BufSize,sizeof(uint32_t));
    sparse_A.index = mxCalloc(BufSize,sizeof(sparse_A.index[0]));
    sparse_A.value = mxCalloc(BufSize,sizeof(sparse_A.value[0]));
    if(sparse_A.nz_dims == NULL || sparse_A.index == NULL || sparse_A.value == NULL) 
      mexErrMsgTxt("Not enough memory for cutting plane buffer sparse_A.");  

    init_time=get_time()-init_time;

    if(verb)
    {
      mexPrintf("Starting optimization:\n");

      if(num_of_Cs == 1)
      {
        ocas = svm_ocas_solver( C, nData, TolRel, TolAbs, QPBound, MaxTime,BufSize, Method, 
                              &sparse_compute_W, &sparse_update_W, &sparse_add_new_cut, 
                              &sparse_compute_output, &qsort_data, &ocas_print, 0);
      }  
      else
      {
        ocas = svm_ocas_solver_difC( vec_C, nData, TolRel, TolAbs, QPBound, MaxTime,BufSize, Method, 
                                     &sparse_compute_W, &sparse_update_W, &sparse_add_new_cut, 
                                     &sparse_compute_output, &qsort_data, &ocas_print, 0);
      }  

    }
    else
    {
      if(num_of_Cs == 1)
      {
        ocas = svm_ocas_solver( C, nData, TolRel, TolAbs, QPBound, MaxTime,BufSize, Method, 
                              &sparse_compute_W, &sparse_update_W, &sparse_add_new_cut, 
                              &sparse_compute_output, &qsort_data, &ocas_print_null, 0);
      }
      else
      {
        ocas = svm_ocas_solver_difC( vec_C, nData, TolRel, TolAbs, QPBound, MaxTime,BufSize, Method, 
                              &sparse_compute_W, &sparse_update_W, &sparse_add_new_cut, 
                              &sparse_compute_output, &qsort_data, &ocas_print_null, 0);
      }
    }

  }
  else
  {

    ptr = mxGetPr(data_X);
    for(i=0; i < nData; i++) {
      for(j=0; j < nDim; j++ ) {
        ptr[LIBOCAS_INDEX(j,i,nDim)] = ptr[LIBOCAS_INDEX(j,i,nDim)]*data_y[i];
      }
    }

    /* init cutting plane buffer */
    full_A = mxCalloc(BufSize*nDim,sizeof(double));
    if( full_A == NULL )
      mexErrMsgTxt("Not enough memory for cutting plane buffer full_A.");    

    init_time=get_time()-init_time;

    if(verb)
    {
      mexPrintf("Starting optimization:\n");
    
      if(num_of_Cs == 1)
        ocas = svm_ocas_solver( C, nData, TolRel, TolAbs, QPBound, MaxTime,BufSize, Method, 
                                &full_compute_W, &full_update_W, &full_add_new_cut, 
                                &full_compute_output, &qsort_data, &ocas_print, 0);
      else
        ocas = svm_ocas_solver_difC( vec_C, nData, TolRel, TolAbs, QPBound, MaxTime,BufSize, Method, 
                                &full_compute_W, &full_update_W, &full_add_new_cut, 
                                &full_compute_output, &qsort_data, &ocas_print, 0);

    }
    else
    {
      if(num_of_Cs == 1)
        ocas = svm_ocas_solver( C, nData, TolRel, TolAbs, QPBound, MaxTime,BufSize, Method, 
                                &full_compute_W, &full_update_W, &full_add_new_cut, 
                                &full_compute_output, &qsort_data, &ocas_print_null, 0);
      else
        ocas = svm_ocas_solver_difC( vec_C, nData, TolRel, TolAbs, QPBound, MaxTime,BufSize, Method, 
                                     &full_compute_W, &full_update_W, &full_add_new_cut, 
                                     &full_compute_output, &qsort_data, &ocas_print_null, 0);
    }
  }

  if(verb)
  {
    mexPrintf("Stopping condition: ");
    switch( ocas.exitflag )
    {
       case 1: mexPrintf("1-Q_D/Q_P <= TolRel(=%f) satisfied.\n", TolRel); break;
       case 2: mexPrintf("Q_P-Q_D <= TolAbs(=%f) satisfied.\n", TolAbs); break;
       case 3: mexPrintf("Q_P <= QPBound(=%f) satisfied.\n", QPBound); break;
       case 4: mexPrintf("Optimization time (=%f) >= MaxTime(=%f).\n", ocas.ocas_time, MaxTime); break;
       case -1: mexPrintf("Has not converged!\n" ); break;
       case -2: mexPrintf("Not enough memory for the solver.\n" ); break;
    }
  }

  total_time=get_time()-total_time;
  if(verb)
  {
    mexPrintf("Timing statistics:\n"
              "   init_time      : %f[s]\n"
              "   qp_solver_time : %f[s]\n"
              "   sort_time      : %f[s]\n"
              "   output_time    : %f[s]\n"
              "   add_time       : %f[s]\n"
              "   w_time         : %f[s]\n"
              "   print_time     : %f[s]\n"
              "   ocas_time      : %f[s]\n"
              "   total_time     : %f[s]\n",
              init_time, ocas.qp_solver_time, ocas.sort_time, ocas.output_time, 
              ocas.add_time, ocas.w_time, ocas.print_time, ocas.ocas_time, total_time);

    mexPrintf("Training error: %.4f%%\n", 100*(double)ocas.trn_err/(double)nData);
  }

  /* multiply data ba labels as it was at the begining */
  if( mxIsSparse(data_X)== true ) {
    /* for i=1:nData, X(:,i) = X(:,i)*y(i); end*/
    for(i=0; i < nData; i++) 
    {
        mul_sparse_col(1/data_y[i], data_X, i);
    }
  }
  else
  {
    ptr = mxGetPr(data_X);
    for(i=0; i < nData; i++) {
      for(j=0; j < nDim; j++ ) {
        ptr[LIBOCAS_INDEX(j,i,nDim)] = ptr[LIBOCAS_INDEX(j,i,nDim)]/data_y[i];
      }
    }
  }

  if(num_of_Cs > 1)
  {
    for(i=0; i < nData; i++) 
      data_y[i] = data_y[i]/vec_C[i];
  }


  plhs[1] = mxCreateDoubleScalar( W0 );
  
  /* return ocas optimizer statistics */
  /* typedef struct {
     uint32_t nIter;    
     uint32_t nCutPlanes;
     double trn_err;      
     double Q_P;          
     double Q_D;
     double output_time;
     double sort_time;
     double solver_time;
     int8_t exitflag;       
     } ocas_return_value_T; */

  const char *field_names[] = {"nTrnErrors","Q_P","Q_D","nIter","nCutPlanes","exitflag",
                               "init_time","output_time","sort_time","qp_solver_time","add_time",
                               "w_time","print_time","ocas_time","total_time"}; 
  mwSize dims[2] = {1,1};  

  plhs[2] = mxCreateStructArray(2, dims, (sizeof(field_names)/sizeof(*field_names)), field_names);
  
  mxSetField(plhs[2],0,"nIter",mxCreateDoubleScalar((double)ocas.nIter));
  mxSetField(plhs[2],0,"nCutPlanes",mxCreateDoubleScalar((double)ocas.nCutPlanes));
  mxSetField(plhs[2],0,"nTrnErrors",mxCreateDoubleScalar(ocas.trn_err)); 
  mxSetField(plhs[2],0,"Q_P",mxCreateDoubleScalar(ocas.Q_P)); 
  mxSetField(plhs[2],0,"Q_D",mxCreateDoubleScalar(ocas.Q_D)); 
  mxSetField(plhs[2],0,"init_time",mxCreateDoubleScalar(init_time)); 
  mxSetField(plhs[2],0,"output_time",mxCreateDoubleScalar(ocas.output_time)); 
  mxSetField(plhs[2],0,"sort_time",mxCreateDoubleScalar(ocas.sort_time)); 
  mxSetField(plhs[2],0,"qp_solver_time",mxCreateDoubleScalar(ocas.qp_solver_time)); 
  mxSetField(plhs[2],0,"add_time",mxCreateDoubleScalar(ocas.add_time)); 
  mxSetField(plhs[2],0,"w_time",mxCreateDoubleScalar(ocas.w_time)); 
  mxSetField(plhs[2],0,"print_time",mxCreateDoubleScalar(ocas.print_time)); 
  mxSetField(plhs[2],0,"ocas_time",mxCreateDoubleScalar(ocas.ocas_time)); 
  mxSetField(plhs[2],0,"total_time",mxCreateDoubleScalar(total_time)); 
  mxSetField(plhs[2],0,"exitflag",mxCreateDoubleScalar((double)ocas.exitflag)); 

  return;
}
Пример #30
0
void mexFunction( int nlhs, mxArray *plhs[],int nrhs, const mxArray *prhs[] )
{
  
  char strFileName[MAXSTRING];
  double record_offset;
  unsigned long file_size;
  FILE *fid=NULL;
  unsigned long nrecords = 0;
  char tval[6];
  double recid;
  uint32_t timestamp = 0;
  int i;
  uint32_t offset;

  /*create empty outputs*/
  for (i=0; i<nlhs; i++) {
    plhs[i] = mxCreateDoubleMatrix(0,0,mxREAL);
  }

  if (nrhs!=3)
    mexErrMsgTxt("Incorrect number of input arguments.");

/*   if (nlhs!=3) */
/*     mexErrMsgTxt("Incorrect number of output arguments."); */

  if (!mxIsChar(prhs[0]))
    mexErrMsgTxt("First argument should be a string");

  if (!mxIsDouble(prhs[1]))
    mexErrMsgTxt("Second argument should be a double");

  if (!mxIsDouble(prhs[2]))
    mexErrMsgTxt("Third argument should be a double");

  mxGetString(prhs[0], strFileName, MAXSTRING);
  if ( (fid = fopen(strFileName, "rb")) == NULL )
    mexErrMsgTxt("Unable to open file");

  recid = mxGetScalar(prhs[2]);
  record_offset = mxGetScalar(prhs[1]);

  fseek(fid, 0, 2);
  file_size = ftell(fid);

  if (record_offset > file_size)
    mexErrMsgTxt("Invalid record offset");

  fseek(fid, record_offset, 0);

  nrecords = 0;
  /*find the number of records in the file and store offsets*/
  while (1) {

    if (fread(tval, 1, 6, fid)==6) {
      offset = ftell(fid)-6;
      if (mxIsInf(recid)==0 && (nrecords == recid)) {
	  timestamp = *((uint32_t*)(&(tval[2])));
	  break;
      }
      nrecords++;
      fseek(fid, ((unsigned char*)tval)[0] * 3, SEEK_CUR);
    } else {
      if (nrecords == 0) {
	offset = record_offset;
	timestamp = 0;
     } else
	timestamp = *((uint32_t*)(&(tval[2])));
      break;
    }
  }

  if (nlhs>0)
    plhs[0] = mxCreateDoubleScalar( nrecords );
  if (nlhs>1)
    plhs[1] = mxCreateDoubleScalar( offset );
  if (nlhs>2)
    plhs[2] = mxCreateDoubleScalar( timestamp );

  fclose(fid);

}