/** * Create a new sparse matrix (uses MALLOC!) */ spmat* newSparseMatrix(idxint m, idxint n, idxint nnz) { idxint* jc = (idxint *)MALLOC((n+1)*sizeof(idxint)); idxint* ir = (idxint *)MALLOC(nnz*sizeof(idxint)); pfloat* pr = (pfloat *)MALLOC(nnz*sizeof(pfloat)); jc[n] = nnz; return createSparseMatrix(m, n, nnz, jc, ir, pr); }
int CreateSparseVariable(int iVar, matvar_t *matVariable, int * parent, int item_position) { int K = 0; sparse_t *sparseData = NULL; SciSparse *scilabSparse = NULL; SciSparse *scilabSparseT = NULL; /* Transpose */ int *colIndexes = NULL; int *rowIndexes = NULL; int *workArray = NULL; struct ComplexSplit *complexData = NULL; SciErr _SciErr; sparseData = (sparse_t*) matVariable->data; scilabSparse = (SciSparse*) MALLOC(sizeof(SciSparse)); if (scilabSparse==NULL) { Scierror(999, _("%s: No more memory.\n"), "CreateSparseVariable"); return FALSE; } /* Computes column indexes from Matlab indexes */ if (sparseData->njc > 1) { colIndexes = (int*) MALLOC(sizeof(int) * (sparseData->njc-1)); if (colIndexes==NULL) { Scierror(999, _("%s: No more memory.\n"), "CreateSparseVariable"); return FALSE; } for (K=0; K<sparseData->njc-1; K++) { colIndexes[K] = sparseData->jc[K+1] - sparseData->jc[K]; } } /* Computes row indexes from Matlab indexes */ rowIndexes = (int*) MALLOC(sizeof(int) * sparseData->nir); if (rowIndexes==NULL) { Scierror(999, _("%s: No more memory.\n"), "CreateSparseVariable"); return FALSE; } for (K=0; K<sparseData->nir; K++) { rowIndexes[K] = sparseData->ir[K] + 1; } /* Create sparse matrix to be transposed */ scilabSparse->m = matVariable->dims[1]; scilabSparse->n = matVariable->dims[0]; scilabSparse->it = matVariable->isComplex; scilabSparse->nel = sparseData->ndata; scilabSparse->mnel = colIndexes; scilabSparse->icol = rowIndexes; if (scilabSparse->it == 0) { scilabSparse->R = (double*) sparseData->data; scilabSparse->I = NULL; } else { complexData = (struct ComplexSplit *) sparseData->data; scilabSparse->R = (double *) complexData->Re; scilabSparse->I = (double *) complexData->Im; } /* Create transpose */ scilabSparseT = (SciSparse*) MALLOC(sizeof(SciSparse)); if (scilabSparseT==NULL) { Scierror(999, _("%s: No more memory.\n"), "CreateSparseVariable"); return FALSE; } scilabSparseT->m = scilabSparse->n; scilabSparseT->n = scilabSparse->m; scilabSparseT->it = scilabSparse->it; scilabSparseT->nel = scilabSparse->nel; if (scilabSparseT->m == 0) { workArray = (int*) MALLOC(sizeof(int)); } else { workArray = (int*) MALLOC(sizeof(int) * scilabSparseT->m); } if (workArray==NULL) { Scierror(999, _("%s: No more memory.\n"), "CreateSparseVariable"); return FALSE; } if (scilabSparseT->m != 0) { scilabSparseT->mnel = (int*) MALLOC(sizeof(int) * scilabSparseT->m); if (scilabSparseT->mnel==NULL) { Scierror(999, _("%s: No more memory.\n"), "CreateSparseVariable"); return FALSE; } } if (scilabSparseT->nel != 0) { scilabSparseT->icol = (int*) MALLOC(sizeof(int) * scilabSparseT->nel); if (scilabSparseT->icol==NULL) { Scierror(999, _("%s: No more memory.\n"), "CreateSparseVariable"); return FALSE; } } if (scilabSparseT->nel != 0) { scilabSparseT->R = (double*) MALLOC(sizeof(double) * scilabSparseT->nel); if (scilabSparseT->R==NULL) { Scierror(999, _("%s: No more memory.\n"), "CreateSparseVariable"); return FALSE; } } if (scilabSparseT->it) { scilabSparseT->I = (double*) MALLOC(sizeof(double) * scilabSparseT->nel); if (scilabSparseT->I==NULL) { Scierror(999, _("%s: No more memory.\n"), "CreateSparseVariable"); return FALSE; } } C2F(spt)(&scilabSparse->m, &scilabSparse->n, &scilabSparse->nel, &scilabSparse->it, workArray, scilabSparse->R, scilabSparse->I, scilabSparse->mnel, scilabSparse->icol, scilabSparseT->R, scilabSparseT->I, scilabSparseT->mnel, scilabSparseT->icol); if (scilabSparse->it) { if (parent==NULL) { _SciErr = createComplexSparseMatrix(pvApiCtx, iVar, scilabSparse->m, scilabSparse->n, scilabSparse->nel, scilabSparseT->mnel, scilabSparseT->icol, scilabSparseT->R, scilabSparseT->I); } else { _SciErr = createComplexSparseMatrixInList(pvApiCtx, iVar, parent, item_position, scilabSparse->m, scilabSparse->n, scilabSparse->nel, scilabSparseT->mnel, scilabSparseT->icol, scilabSparseT->R, scilabSparseT->I); } } else { if (parent==NULL) { _SciErr = createSparseMatrix(pvApiCtx, iVar, scilabSparseT->m, scilabSparseT->n, scilabSparseT->nel, scilabSparseT->mnel, scilabSparseT->icol, scilabSparseT->R); } else { _SciErr = createSparseMatrixInList(pvApiCtx, iVar, parent, item_position, scilabSparseT->m, scilabSparseT->n, scilabSparseT->nel, scilabSparseT->mnel, scilabSparseT->icol, scilabSparseT->R); } } /* Free all arrays */ if (scilabSparse != NULL) FREE(scilabSparse); if (colIndexes != NULL) FREE(colIndexes); if (rowIndexes != NULL) FREE(rowIndexes); if (workArray != NULL) FREE(workArray); if (scilabSparseT->m != 0) FREE(scilabSparseT->mnel); if (scilabSparseT->nel != 0) FREE(scilabSparseT->icol); if (scilabSparseT->nel != 0) FREE(scilabSparseT->R); if ((scilabSparseT->nel != 0) && (scilabSparseT->it != 0)) FREE(scilabSparseT->I); if (scilabSparseT != NULL) FREE(scilabSparseT); return TRUE; }
/* * Builds KKT matrix. * We store and operate only on the upper triangular part. * Replace by or use in codegen. * * INPUT: spmat* Gt - pointer to G' * spmat* At - pointer to A' * cone* C - pointer to cone struct * * OUTPUT: idxint* Sign - pointer to vector of signs for regularization * spmat* K - pointer to unpermuted upper triangular part of KKT matrix */ void createKKT_U(spmat* Gt, spmat* At, cone* C, idxint** S, spmat** K) { idxint i, j, k, l, r, row_stop, row, cone_strt, ks, conesize; idxint n = Gt->m; idxint m = Gt->n; idxint p = At ? At->n : 0; idxint nK, nnzK; pfloat *Kpr; idxint *Kjc, *Kir; idxint *Sign; /* Dimension of KKT matrix * = n (number of variables) * + p (number of equality constraints) * + m (number of inequality constraints) * + 2*C->nsoc (expansion of SOC scalings) */ nK = n + p + m; #if CONEMODE == 0 nK += 2*C->nsoc; #endif /* Number of non-zeros in KKT matrix * = At->nnz (nnz of equality constraint matrix A) * + Gt->nnz (nnz of inequality constraint matrix) * + C->lpc.p (nnz of LP cone) * + 3*[sum(C->soc[i].p)+1] (nnz of expanded soc scalings) */ nnzK = (At ? At->nnz : 0) + Gt->nnz + C->lpc->p; #if STATICREG == 1 nnzK += n+p; #endif for( i=0; i<C->nsoc; i++ ){ #if CONEMODE == 0 nnzK += 3*C->soc[i].p+1; #else nnzK += (C->soc[i].p*(C->soc[i].p+1))/2; #endif } #if PRINTLEVEL > 2 PRINTTEXT("Non-zeros in KKT matrix: %d\n", (int) nnzK); #endif /* Allocate memory for KKT matrix */ Kpr = (pfloat *)MALLOC(nnzK*sizeof(pfloat)); Kir = (idxint *)MALLOC(nnzK*sizeof(idxint)); Kjc = (idxint *)MALLOC((nK+1)*sizeof(idxint)); /* Allocate memory for sign vector */ Sign = (idxint *)MALLOC(nK*sizeof(idxint)); #if PRINTLEVEL > 2 PRINTTEXT("Memory allocated for sign vector\n"); #endif /* Set signs for regularization of (1,1) block */ for( ks=0; ks < n; ks++ ){ Sign[ks] = +1; /* (1,1) block */ } for( ks=n; ks < n+p; ks++){ Sign[ks] = -1; /* (2,2) block */ } #if CONEMODE == 0 for( ks=n+p; ks < n+p+C->lpc->p; ks++){ Sign[ks] = -1; /* (3,3) block: LP cone */ } ks = n+p+C->lpc->p; for( l=0; l<C->nsoc; l++){ for (i=0; i<C->soc[l].p; i++) { Sign[ks++] = -1; /* (3,3) block: SOC, D */ } Sign[ks++] = -1; /* (3,3) block: SOC, v */ Sign[ks++] = +1; /* (3,3) block: SOC, u */ } #else for (ks=n+p; ks < n+p+m; ks++) { Sign[ks] = -1; /* (3,3) block has -1 sign if all dense */ } #endif #if DEBUG > 0 if (ks!=nK) { PRINTTEXT("ks = %d, whereas nK = %d - exiting.", (int)ks, (int)nK); exit(-1); } #endif /* count the number of non-zero entries in K */ k = 0; /* (1,1) block: the first n columns are empty */ #if STATICREG == 0 for (j=0; j<n; j++) { Kjc[j] = 0; } #else for (j=0; j<n; j++) { Kjc[j] = j; Kir[j] = j; Kpr[k++] = DELTASTAT; } #endif /* Fill upper triangular part of K with values */ /* (1,2) block: A' */ i = 0; /* counter for non-zero entries in A or G, respectively */ for( j=0; j<p; j++ ){ /* A' */ row = At->jc[j]; row_stop = At->jc[j+1]; if( row <= row_stop ){ Kjc[n+j] = k; while( row++ < row_stop ){ Kir[k] = At->ir[i]; Kpr[k] = At->pr[i]; k++; i++; } } #if STATICREG == 1 Kir[k] = n+j; Kpr[k++] = -DELTASTAT; #endif } /* (1,3) and (3,3) block: [G'; 0; -Vinit] * where * * Vinit = blkdiag(I, blkdiag(I,1,-1), ..., blkdiag(I,1,-1)); * ^ #number of second-order cones ^ * * Note that we have to prepare the (3,3) block accordingly * (put zeros for init but store indices that are used in KKT_update * of cone module) */ /* LP cone */ i = 0; for( j=0; j < C->lpc->p; j++ ){ /* copy in G' */ row = Gt->jc[j]; row_stop = Gt->jc[j+1]; if( row <= row_stop ){ Kjc[n+p+j] = k; while( row++ < row_stop ){ Kir[k] = Gt->ir[i]; Kpr[k] = Gt->pr[i]; k++; i++; } } /* -I for LP-cone */ C->lpc->kkt_idx[j] = k; Kir[k] = n+p+j; Kpr[k] = -1.0; k++; } #if CONEMODE == 0 /* Second-order cones - copy in G' and set up the scaling matrix * which has the following structure: * * * [ * 0 * ] * [ * * * ] * [ * * * ] [ I v u ] I: identity of size conesize * - [ * * * ] = -[ u' 1 0 ] v: vector of size conesize - 1 * [ * * * ] [ v' 0' -1 ] u: vector of size conesize * [ * * * ] * [ * * * ] * [ 0 * * * * * * 1 0 ] * [ * * * * * * * 0 -1 ] * * NOTE: only the upper triangular part (with the diagonal elements) * is copied in here. */ cone_strt = C->lpc->p; for( l=0; l < C->nsoc; l++ ){ /* size of the cone */ conesize = C->soc[l].p; /* go column-wise about it */ for( j=0; j < conesize; j++ ){ row = Gt->jc[cone_strt+j]; row_stop = Gt->jc[cone_strt+j+1]; if( row <= row_stop ){ Kjc[n+p+cone_strt+2*l+j] = k; while( row++ < row_stop ){ Kir[k] = Gt->ir[i]; Kpr[k++] = Gt->pr[i++]; } } /* diagonal D */ Kir[k] = n+p+cone_strt + 2*l + j; Kpr[k] = -1.0; C->soc[l].Didx[j] = k; k++; } /* v */ Kjc[n+p+cone_strt+2*l+conesize] = k; for (r=1; r<conesize; r++) { Kir[k] = n+p+cone_strt + 2*l + r; Kpr[k] = 0; k++; } Kir[k] = n+p+cone_strt + 2*l + conesize; Kpr[k] = -1; k++; /* u */ Kjc[n+p+cone_strt+2*l+conesize+1] = k; for (r=0; r<conesize; r++) { Kir[k] = n+p+cone_strt + 2*l + r; Kpr[k] = 0; k++; } Kir[k] = n+p+cone_strt + 2*l + conesize + 1; Kpr[k] = +1; k++; /* prepare index for next cone */ cone_strt += C->soc[l].p; } #else /* Second-order cones - copy in G' and set up the scaling matrix * which has a dense structure (only upper half part is shown): * * [ a b*q' ] * - W^2 = -V = eta^2 [ b*q I + c*(q*q') ] * * where I: identity of size conesize * q: vector of size consize - 1 * a,b,c: scalars * * NOTE: only the upper triangular part (with the diagonal elements) * is copied in here. */ cone_strt = C->lpc->p; for( l=0; l < C->nsoc; l++ ){ /* size of the cone */ conesize = C->soc[l].p; /* go column-wise about it */ for( j=0; j < conesize; j++ ){ row = Gt->jc[cone_strt+j]; row_stop = Gt->jc[cone_strt+j+1]; if( row <= row_stop ){ Kjc[n+p+cone_strt+j] = k; while( row++ < row_stop ){ Kir[k] = Gt->ir[i]; Kpr[k++] = Gt->pr[i++]; } } /* first elements - record where this column starts */ Kir[k] = n+p+cone_strt; Kpr[k] = -1.0; C->soc[l].colstart[j] = k; k++; /* the rest of the column */ for (r=1; r<=j; r++) { Kir[k] = n+p+cone_strt+r; Kpr[k] = -1.0; k++; } } /* prepare index for next cone */ cone_strt += C->soc[l].p; } #endif #if PRINTLEVEL > 2 PRINTTEXT("CREATEKKT: Written %d KKT entries\n", (int)k); PRINTTEXT("CREATEKKT: nK=%d and ks=%d\n",(int)nK,(int)ks); PRINTTEXT("CREATEKKT: Size of KKT matrix: %d\n", (int)nK); #endif /* return Sign vector and KKT matrix */ *S = Sign; *K = createSparseMatrix(nK, nK, nnzK, Kjc, Kir, Kpr); }
/* * Sets up all data structures needed. * Replace by codegen */ pwork* ECOS_setup(idxint n, idxint m, idxint p, idxint l, idxint ncones, idxint* q, pfloat* Gpr, idxint* Gjc, idxint* Gir, pfloat* Apr, idxint* Ajc, idxint* Air, pfloat* c, pfloat* h, pfloat* b) { idxint i, j, k, cidx, conesize, lnz, amd_result, nK, *Ljc, *Lir, *P, *Pinv, *Sign; pwork* mywork; double Control [AMD_CONTROL], Info [AMD_INFO]; pfloat rx, ry, rz, *Lpr; spmat *At, *Gt, *KU; #if PROFILING > 0 timer tsetup; #endif #if PROFILING > 1 timer tcreatekkt; timer tmattranspose; timer tordering; #endif #if PROFILING > 0 tic(&tsetup); #endif #if PRINTLEVEL > 2 PRINTTEXT("\n"); PRINTTEXT(" *******************************************************************************\n"); PRINTTEXT(" * ECOS: Embedded Conic Solver - Sparse Interior Point method for SOCPs *\n"); PRINTTEXT(" * *\n"); PRINTTEXT(" * NOTE: The solver is based on L. Vandenberghe's 'The CVXOPT linear and quad- *\n"); PRINTTEXT(" * ratic cone program solvers', March 20, 2010. Available online: *\n"); PRINTTEXT(" * [http://abel.ee.ucla.edu/cvxopt/documentation/coneprog.pdf] *\n"); PRINTTEXT(" * *\n"); PRINTTEXT(" * This code uses T.A. Davis' sparse LDL package and AMD code. *\n"); PRINTTEXT(" * [http://www.cise.ufl.edu/research/sparse] *\n"); PRINTTEXT(" * *\n"); PRINTTEXT(" * Written during a summer visit at Stanford University with S. Boyd. *\n"); PRINTTEXT(" * *\n"); PRINTTEXT(" * (C) Alexander Domahidi, Automatic Control Laboratory, ETH Zurich, 2012-13. *\n"); PRINTTEXT(" * Email: [email protected] *\n"); PRINTTEXT(" *******************************************************************************\n"); PRINTTEXT("\n\n"); PRINTTEXT("PROBLEM SUMMARY:\n"); PRINTTEXT(" Primal variables (n): %d\n", (int)n); PRINTTEXT("Equality constraints (p): %d\n", (int)p); PRINTTEXT(" Conic variables (m): %d\n", (int)m); PRINTTEXT("- - - - - - - - - - - - - - -\n"); PRINTTEXT(" Size of LP cone: %d\n", (int)l); PRINTTEXT(" Number of SOCs: %d\n", (int)ncones); for( i=0; i<ncones; i++ ){ PRINTTEXT(" Size of SOC #%02d: %d\n", (int)(i+1), (int)q[i]); } #endif /* get work data structure */ mywork = (pwork *)MALLOC(sizeof(pwork)); #if PRINTLEVEL > 2 PRINTTEXT("Memory allocated for WORK struct\n"); #endif /* dimensions */ mywork->n = n; mywork->m = m; mywork->p = p; mywork->D = l + ncones; #if PRINTLEVEL > 2 PRINTTEXT("Set dimensions\n"); #endif /* variables */ mywork->x = (pfloat *)MALLOC(n*sizeof(pfloat)); mywork->y = (pfloat *)MALLOC(p*sizeof(pfloat)); mywork->z = (pfloat *)MALLOC(m*sizeof(pfloat)); mywork->s = (pfloat *)MALLOC(m*sizeof(pfloat)); mywork->lambda = (pfloat *)MALLOC(m*sizeof(pfloat)); mywork->dsaff_by_W = (pfloat *)MALLOC(m*sizeof(pfloat)); mywork->dsaff = (pfloat *)MALLOC(m*sizeof(pfloat)); mywork->dzaff = (pfloat *)MALLOC(m*sizeof(pfloat)); mywork->saff = (pfloat *)MALLOC(m*sizeof(pfloat)); mywork->zaff = (pfloat *)MALLOC(m*sizeof(pfloat)); mywork->W_times_dzaff = (pfloat *)MALLOC(m*sizeof(pfloat)); #if PRINTLEVEL > 2 PRINTTEXT("Memory allocated for variables\n"); #endif /* best iterates so far */ mywork->best_x = (pfloat *)MALLOC(n*sizeof(pfloat)); mywork->best_y = (pfloat *)MALLOC(p*sizeof(pfloat)); mywork->best_z = (pfloat *)MALLOC(m*sizeof(pfloat)); mywork->best_s = (pfloat *)MALLOC(m*sizeof(pfloat)); mywork->best_info = (stats *)MALLOC(sizeof(stats)); /* cones */ mywork->C = (cone *)MALLOC(sizeof(cone)); #if PRINTLEVEL > 2 PRINTTEXT("Memory allocated for cone struct\n"); #endif /* LP cone */ mywork->C->lpc = (lpcone *)MALLOC(sizeof(lpcone)); mywork->C->lpc->p = l; if( l > 0 ){ mywork->C->lpc->w = (pfloat *)MALLOC(l*sizeof(pfloat)); mywork->C->lpc->v = (pfloat *)MALLOC(l*sizeof(pfloat)); mywork->C->lpc->kkt_idx = (idxint *)MALLOC(l*sizeof(idxint)); #if PRINTLEVEL > 2 PRINTTEXT("Memory allocated for LP cone\n"); #endif } else { mywork->C->lpc->w = NULL; mywork->C->lpc->v = NULL; mywork->C->lpc->kkt_idx = NULL; #if PRINTLEVEL > 2 PRINTTEXT("No LP cone present, pointers filled with NULL\n"); #endif } /* Second-order cones */ mywork->C->soc = (socone *)MALLOC(ncones*sizeof(socone)); mywork->C->nsoc = ncones; cidx = 0; for( i=0; i<ncones; i++ ){ conesize = (idxint)q[i]; mywork->C->soc[i].p = conesize; mywork->C->soc[i].a = 0; mywork->C->soc[i].eta = 0; mywork->C->soc[i].q = (pfloat *)MALLOC((conesize-1)*sizeof(pfloat)); mywork->C->soc[i].skbar = (pfloat *)MALLOC((conesize)*sizeof(pfloat)); mywork->C->soc[i].zkbar = (pfloat *)MALLOC((conesize)*sizeof(pfloat)); #if CONEMODE == 0 mywork->C->soc[i].Didx = (idxint *)MALLOC((conesize)*sizeof(idxint)); #endif #if CONEMODE > 0 mywork->C->soc[i].colstart = (idxint *)MALLOC((conesize)*sizeof(idxint)); #endif cidx += conesize; } #if PRINTLEVEL > 2 PRINTTEXT("Memory allocated for second-order cones\n"); #endif /* info struct */ mywork->info = (stats *)MALLOC(sizeof(stats)); #if PROFILING > 1 mywork->info->tfactor = 0; mywork->info->tkktsolve = 0; mywork->info->tfactor_t1 = 0; mywork->info->tfactor_t2 = 0; #endif #if PRINTLEVEL > 2 PRINTTEXT("Memory allocated for info struct\n"); #endif #if defined EQUILIBRATE && EQUILIBRATE > 0 /* equilibration vector */ mywork->xequil = (pfloat *)MALLOC(n*sizeof(pfloat)); mywork->Aequil = (pfloat *)MALLOC(p*sizeof(pfloat)); mywork->Gequil = (pfloat *)MALLOC(m*sizeof(pfloat)); #if PRINTLEVEL > 2 PRINTTEXT("Memory allocated for equilibration vectors\n"); #endif #endif /* settings */ mywork->stgs = (settings *)MALLOC(sizeof(settings)); mywork->stgs->maxit = MAXIT; mywork->stgs->gamma = GAMMA; mywork->stgs->delta = DELTA; mywork->stgs->eps = EPS; mywork->stgs->nitref = NITREF; mywork->stgs->abstol = ABSTOL; mywork->stgs->feastol = FEASTOL; mywork->stgs->reltol = RELTOL; mywork->stgs->abstol_inacc = ATOL_INACC; mywork->stgs->feastol_inacc = FTOL_INACC; mywork->stgs->reltol_inacc = RTOL_INACC; mywork->stgs->verbose = VERBOSE; #if PRINTLEVEL > 2 PRINTTEXT("Written settings\n"); #endif mywork->c = c; mywork->h = h; mywork->b = b; #if PRINTLEVEL > 2 PRINTTEXT("Hung pointers for c, h and b into WORK struct\n"); #endif /* Store problem data */ if(Apr && Ajc && Air) { mywork->A = createSparseMatrix(p, n, Ajc[n], Ajc, Air, Apr); } else { mywork->A = NULL; } if (Gpr && Gjc && Gir) { mywork->G = createSparseMatrix(m, n, Gjc[n], Gjc, Gir, Gpr); } else { /* create an empty sparse matrix */ mywork->G = createSparseMatrix(m, n, 0, Gjc, Gir, Gpr); } #if defined EQUILIBRATE && EQUILIBRATE > 0 set_equilibration(mywork); #if PRINTLEVEL > 2 PRINTTEXT("Done equilibrating\n"); #endif #endif #if PROFILING > 1 mywork->info->ttranspose = 0; tic(&tmattranspose); #endif if(mywork->A) At = transposeSparseMatrix(mywork->A); else At = NULL; #if PROFILING > 1 mywork->info->ttranspose += toc(&tmattranspose); #endif #if PRINTLEVEL > 2 PRINTTEXT("Transposed A\n"); #endif #if PROFILING > 1 tic(&tmattranspose); #endif Gt = transposeSparseMatrix(mywork->G); #if PROFILING > 1 mywork->info->ttranspose += toc(&tmattranspose); #endif #if PRINTLEVEL > 2 PRINTTEXT("Transposed G\n"); #endif /* set up KKT system */ #if PROFILING > 1 tic(&tcreatekkt); #endif createKKT_U(Gt, At, mywork->C, &Sign, &KU); #if PROFILING > 1 mywork->info->tkktcreate = toc(&tcreatekkt); #endif #if PRINTLEVEL > 2 PRINTTEXT("Created upper part of KKT matrix K\n"); #endif /* * Set up KKT system related data * (L comes later after symbolic factorization) */ nK = KU->n; #if DEBUG > 0 dumpSparseMatrix(KU, "KU0.txt"); #endif #if PRINTLEVEL > 2 PRINTTEXT("Dimension of KKT matrix: %d\n", (int)nK); PRINTTEXT("Non-zeros in KKT matrix: %d\n", (int)KU->nnz); #endif /* allocate memory in KKT system */ mywork->KKT = (kkt *)MALLOC(sizeof(kkt)); mywork->KKT->D = (pfloat *)MALLOC(nK*sizeof(pfloat)); mywork->KKT->Parent = (idxint *)MALLOC(nK*sizeof(idxint)); mywork->KKT->Pinv = (idxint *)MALLOC(nK*sizeof(idxint)); mywork->KKT->work1 = (pfloat *)MALLOC(nK*sizeof(pfloat)); mywork->KKT->work2 = (pfloat *)MALLOC(nK*sizeof(pfloat)); mywork->KKT->work3 = (pfloat *)MALLOC(nK*sizeof(pfloat)); mywork->KKT->work4 = (pfloat *)MALLOC(nK*sizeof(pfloat)); mywork->KKT->work5 = (pfloat *)MALLOC(nK*sizeof(pfloat)); mywork->KKT->work6 = (pfloat *)MALLOC(nK*sizeof(pfloat)); mywork->KKT->Flag = (idxint *)MALLOC(nK*sizeof(idxint)); mywork->KKT->Pattern = (idxint *)MALLOC(nK*sizeof(idxint)); mywork->KKT->Lnz = (idxint *)MALLOC(nK*sizeof(idxint)); mywork->KKT->RHS1 = (pfloat *)MALLOC(nK*sizeof(pfloat)); mywork->KKT->RHS2 = (pfloat *)MALLOC(nK*sizeof(pfloat)); mywork->KKT->dx1 = (pfloat *)MALLOC(mywork->n*sizeof(pfloat)); mywork->KKT->dx2 = (pfloat *)MALLOC(mywork->n*sizeof(pfloat)); mywork->KKT->dy1 = (pfloat *)MALLOC(mywork->p*sizeof(pfloat)); mywork->KKT->dy2 = (pfloat *)MALLOC(mywork->p*sizeof(pfloat)); mywork->KKT->dz1 = (pfloat *)MALLOC(mywork->m*sizeof(pfloat)); mywork->KKT->dz2 = (pfloat *)MALLOC(mywork->m*sizeof(pfloat)); mywork->KKT->Sign = (idxint *)MALLOC(nK*sizeof(idxint)); mywork->KKT->PKPt = newSparseMatrix(nK, nK, KU->nnz); mywork->KKT->PK = (idxint *)MALLOC(KU->nnz*sizeof(idxint)); #if PRINTLEVEL > 2 PRINTTEXT("Created memory for KKT-related data\n"); #endif /* calculate ordering of KKT matrix using AMD */ P = (idxint *)MALLOC(nK*sizeof(idxint)); #if PROFILING > 1 tic(&tordering); #endif AMD_defaults(Control); amd_result = AMD_order(nK, KU->jc, KU->ir, P, Control, Info); #if PROFILING > 1 mywork->info->torder = toc(&tordering); #endif if( amd_result == AMD_OK ){ #if PRINTLEVEL > 2 PRINTTEXT("AMD ordering successfully computed.\n"); AMD_info(Info); #endif } else { #if PRINTLEVEL > 2 PRINTTEXT("Problem in AMD ordering, exiting.\n"); AMD_info(Info); #endif return NULL; } /* calculate inverse permutation and permutation mapping of KKT matrix */ pinv(nK, P, mywork->KKT->Pinv); Pinv = mywork->KKT->Pinv; #if DEBUG > 0 dumpDenseMatrix_i(P, nK, 1, "P.txt"); dumpDenseMatrix_i(mywork->KKT->Pinv, nK, 1, "PINV.txt"); #endif permuteSparseSymmetricMatrix(KU, mywork->KKT->Pinv, mywork->KKT->PKPt, mywork->KKT->PK); /* permute sign vector */ for( i=0; i<nK; i++ ){ mywork->KKT->Sign[Pinv[i]] = Sign[i]; } #if PRINTLEVEL > 3 PRINTTEXT("P = ["); for( i=0; i<nK; i++ ){ PRINTTEXT("%d ", (int)P[i]); } PRINTTEXT("];\n"); PRINTTEXT("Pinv = ["); for( i=0; i<nK; i++ ){ PRINTTEXT("%d ", (int)Pinv[i]); } PRINTTEXT("];\n"); PRINTTEXT("Sign = ["); for( i=0; i<nK; i++ ){ PRINTTEXT("%+d ", (int)Sign[i]); } PRINTTEXT("];\n"); PRINTTEXT("SignP = ["); for( i=0; i<nK; i++ ){ PRINTTEXT("%+d ", (int)mywork->KKT->Sign[i]); } PRINTTEXT("];\n"); #endif /* symbolic factorization */ Ljc = (idxint *)MALLOC((nK+1)*sizeof(idxint)); #if PRINTLEVEL > 2 PRINTTEXT("Allocated memory for cholesky factor L\n"); #endif LDL_symbolic2( mywork->KKT->PKPt->n, /* A and L are n-by-n, where n >= 0 */ mywork->KKT->PKPt->jc, /* input of size n+1, not modified */ mywork->KKT->PKPt->ir, /* input of size nz=Ap[n], not modified */ Ljc, /* output of size n+1, not defined on input */ mywork->KKT->Parent, /* output of size n, not defined on input */ mywork->KKT->Lnz, /* output of size n, not defined on input */ mywork->KKT->Flag /* workspace of size n, not defn. on input or output */ ); /* assign memory for L */ lnz = Ljc[nK]; #if PRINTLEVEL > 2 PRINTTEXT("Nonzeros in L, excluding diagonal: %d\n", (int)lnz) ; #endif Lir = (idxint *)MALLOC(lnz*sizeof(idxint)); Lpr = (pfloat *)MALLOC(lnz*sizeof(pfloat)); mywork->KKT->L = createSparseMatrix(nK, nK, lnz, Ljc, Lir, Lpr); #if PRINTLEVEL > 2 PRINTTEXT("Created Cholesky factor of K in KKT struct\n"); #endif /* permute KKT matrix - we work on this one from now on */ permuteSparseSymmetricMatrix(KU, mywork->KKT->Pinv, mywork->KKT->PKPt, NULL); #if DEBUG > 0 dumpSparseMatrix(mywork->KKT->PKPt, "PKPt.txt"); #endif #if CONEMODE > 0 /* zero any off-diagonal elements in (permuted) scalings in KKT matrix */ for (i=0; i<mywork->C->nsoc; i++) { for (j=1; j<mywork->C->soc[i].p; j++) { for (k=0; k<j; k++) { mywork->KKT->PKPt->pr[mywork->KKT->PK[mywork->C->soc[i].colstart[j]+k]] = 0; } } } #endif #if DEBUG > 0 dumpSparseMatrix(mywork->KKT->PKPt, "PKPt0.txt"); #endif /* set up RHSp for initialization */ k = 0; j = 0; for( i=0; i<n; i++ ){ mywork->KKT->RHS1[Pinv[k++]] = 0; } for( i=0; i<p; i++ ){ mywork->KKT->RHS1[Pinv[k++]] = b[i]; } for( i=0; i<l; i++ ){ mywork->KKT->RHS1[Pinv[k++]] = h[i]; j++; } for( l=0; l<ncones; l++ ){ for( i=0; i < mywork->C->soc[l].p; i++ ){ mywork->KKT->RHS1[Pinv[k++]] = h[j++]; } #if CONEMODE == 0 mywork->KKT->RHS1[Pinv[k++]] = 0; mywork->KKT->RHS1[Pinv[k++]] = 0; #endif } #if PRINTLEVEL > 2 PRINTTEXT("Written %d entries of RHS1\n", (int)k); #endif /* set up RHSd for initialization */ for( i=0; i<n; i++ ){ mywork->KKT->RHS2[Pinv[i]] = -c[i]; } for( i=n; i<nK; i++ ){ mywork->KKT->RHS2[Pinv[i]] = 0; } /* get scalings of problem data */ rx = norm2(c, n); mywork->resx0 = MAX(1, rx); ry = norm2(b, p); mywork->resy0 = MAX(1, ry); rz = norm2(h, m); mywork->resz0 = MAX(1, rz); /* get memory for residuals */ mywork->rx = (pfloat *)MALLOC(n*sizeof(pfloat)); mywork->ry = (pfloat *)MALLOC(p*sizeof(pfloat)); mywork->rz = (pfloat *)MALLOC(m*sizeof(pfloat)); /* clean up */ mywork->KKT->P = P; FREE(Sign); if(At) freeSparseMatrix(At); freeSparseMatrix(Gt); freeSparseMatrix(KU); #if PROFILING > 0 mywork->info->tsetup = toc(&tsetup); #endif return mywork; }
int sci_umf_luget(char* fname, void* pvApiCtx) { /* * LU_ptr is (a pointer to) a factorization of A, we have: * -1 * P R A Q = L U * * A is n_row x n_col * L is n_row x n * U is n x n_col n = min(n_row, n_col) */ SciErr sciErr; void* Numeric = NULL; int lnz = 0, unz = 0, n_row = 0, n_col = 0, n = 0, nz_udiag = 0, i = 0, stat = 0, do_recip = 0, it_flag = 0; int *L_mnel = NULL, *L_icol = NULL, *L_ptrow = NULL, *U_mnel = NULL, *U_icol = NULL, *U_ptrow = NULL, *V_irow = NULL, *V_ptcol = NULL; double *L_R = NULL, *L_I = NULL, *U_R = NULL, *U_I = NULL, *V_R = NULL, *V_I = NULL, *Rs = NULL; int *p = NULL, *q = NULL, pl_miss = 0, error_flag = 0 ; int* piAddr1 = NULL; int iType1 = 0; /* Check numbers of input/output arguments */ CheckInputArgument(pvApiCtx, 1, 1); CheckOutputArgument(pvApiCtx, 1, 5); /* get the pointer to the LU factors */ sciErr = getVarAddressFromPosition(pvApiCtx, 1, &piAddr1); if (sciErr.iErr) { printError(&sciErr, 0); return 1; } /* Check if the first argument is a pointer */ sciErr = getVarType(pvApiCtx, piAddr1, &iType1); if (sciErr.iErr || iType1 != sci_pointer) { printError(&sciErr, 0); Scierror(999, _("%s: Wrong type for input argument #%d: A pointer expected.\n"), fname, 1); return 1; } sciErr = getPointer(pvApiCtx, piAddr1, &Numeric); if (sciErr.iErr) { printError(&sciErr, 0); return 1; } /* Check if the pointer is a valid ref to ... */ if ( IsAdrInList(Numeric, ListNumeric, &it_flag) ) { if (it_flag == 0 ) { umfpack_di_get_lunz(&lnz, &unz, &n_row, &n_col, &nz_udiag, Numeric); } else { umfpack_zi_get_lunz(&lnz, &unz, &n_row, &n_col, &nz_udiag, Numeric); } } else { Scierror(999, _("%s: Wrong value for input argument #%d: Must be a valid reference to (umf) LU factors.\n"), fname, 1); return 1; } if (n_row <= n_col) { n = n_row; } else { n = n_col; } L_mnel = (int*)MALLOC(n_row * sizeof(int)); L_icol = (int*)MALLOC(lnz * sizeof(int)); L_ptrow = (int*)MALLOC((n_row + 1) * sizeof(int)); L_R = (double*)MALLOC( lnz * sizeof(double)); U_mnel = (int*)MALLOC(n * sizeof(int)); U_icol = (int*)MALLOC(unz * sizeof(int)); U_ptrow = (int*)MALLOC((n + 1) * sizeof(int)); U_R = (double*)MALLOC( unz * sizeof(double)); V_irow = (int*)MALLOC(unz * sizeof(int)); V_ptcol = (int*)MALLOC((n_col + 1) * sizeof(int)); V_R = (double*)MALLOC( unz * sizeof(double)); p = (int*)MALLOC(n_row * sizeof(int)); q = (int*)MALLOC(n_col * sizeof(int)); Rs = (double*)MALLOC(n_row * sizeof(double)); if ( it_flag == 1 ) { L_I = (double*)MALLOC(lnz * sizeof(double)); U_I = (double*)MALLOC(unz * sizeof(double)); V_I = (double*)MALLOC(unz * sizeof(double)); } else { L_I = U_I = V_I = NULL; } if ( !(L_mnel && L_icol && L_R && L_ptrow && p && U_mnel && U_icol && U_R && U_ptrow && q && V_irow && V_R && V_ptcol && Rs) || (it_flag && !(L_I && U_I && V_I)) ) { error_flag = 1; goto the_end; } if ( it_flag == 0 ) { stat = umfpack_di_get_numeric(L_ptrow, L_icol, L_R, V_ptcol, V_irow, V_R, p, q, (double *)NULL, &do_recip, Rs, Numeric); } else { stat = umfpack_zi_get_numeric(L_ptrow, L_icol, L_R, L_I, V_ptcol, V_irow, V_R, V_I, p, q, (double *)NULL, (double *)NULL, &do_recip, Rs, Numeric); } if ( stat != UMFPACK_OK ) { error_flag = 2; goto the_end; }; if ( do_recip ) { for ( i = 0 ; i < n_row ; i++ ) { Rs[i] = 1.0 / Rs[i]; } } if ( it_flag == 0 ) { stat = umfpack_di_transpose(n, n_col, V_ptcol, V_irow, V_R, (int *) NULL, (int*) NULL, U_ptrow, U_icol, U_R); } else { stat = umfpack_zi_transpose(n, n_col, V_ptcol, V_irow, V_R, V_I, (int *) NULL, (int*) NULL, U_ptrow, U_icol, U_R, U_I, 0); } if ( stat != UMFPACK_OK ) { error_flag = 2; goto the_end; }; for ( i = 0 ; i < n_row ; i++ ) { L_mnel[i] = L_ptrow[i + 1] - L_ptrow[i]; } for ( i = 0 ; i < n ; i++ ) { U_mnel[i] = U_ptrow[i + 1] - U_ptrow[i]; } for ( i = 0 ; i < lnz ; i++ ) { L_icol[i]++; } for ( i = 0 ; i < unz ; i++ ) { U_icol[i]++; } for ( i = 0 ; i < n_row ; i++ ) { p[i]++; } for ( i = 0 ; i < n_col ; i++ ) { q[i]++; } /* output L */ if (it_flag) // complex { sciErr = createComplexSparseMatrix(pvApiCtx, 2, n_row, n, lnz, L_mnel, L_icol, L_R, L_I); } else { sciErr = createSparseMatrix(pvApiCtx, 2, n_row, n, lnz, L_mnel, L_icol, L_R); } if (sciErr.iErr) { printError(&sciErr, 0); FREE(L_mnel); FREE(U_mnel); return 1; } /* output U */ if (it_flag) // complex { sciErr = createComplexSparseMatrix(pvApiCtx, 3, n, n_col, unz, U_mnel, U_icol, U_R, U_I); } else { sciErr = createSparseMatrix(pvApiCtx, 3, n, n_col, unz, U_mnel, U_icol, U_R); } if (sciErr.iErr) { printError(&sciErr, 0); FREE(L_mnel); FREE(U_mnel); return 1; } /* output p */ sciErr = createMatrixOfDoubleAsInteger(pvApiCtx, 4, n_row, 1, p); if (sciErr.iErr) { printError(&sciErr, 0); FREE(L_mnel); FREE(U_mnel); return 1; } /* output q */ sciErr = createMatrixOfDoubleAsInteger(pvApiCtx, 5, n_col, 1, q); if (sciErr.iErr) { printError(&sciErr, 0); FREE(L_mnel); FREE(U_mnel); return 1; } /* output res */ sciErr = createMatrixOfDouble(pvApiCtx, 6, n_row, 1, Rs); if (sciErr.iErr) { printError(&sciErr, 0); FREE(L_mnel); FREE(U_mnel); return 1; } the_end: FREE(L_mnel); FREE(L_icol); FREE(L_R); FREE(L_ptrow); FREE(p); FREE(U_mnel); FREE(U_icol); FREE(U_R); FREE(U_ptrow); FREE(q); FREE(V_irow); FREE(V_R); FREE(V_ptcol); FREE(Rs); if ( it_flag == 1 ) { FREE(L_I); FREE(V_I); FREE(U_I); } switch (error_flag) { case 0: /* no error */ AssignOutputVariable(pvApiCtx, 1) = 2; AssignOutputVariable(pvApiCtx, 2) = 3; AssignOutputVariable(pvApiCtx, 3) = 4; AssignOutputVariable(pvApiCtx, 4) = 5; AssignOutputVariable(pvApiCtx, 5) = 6; ReturnArguments(pvApiCtx); return 0; case 1: /* enough memory (with malloc) */ Scierror(999, _("%s: No more memory.\n"), fname); break; case 2: /* a problem with one umfpack routine */ Scierror(999, "%s: %s\n", fname, UmfErrorMes(stat)); break; } return 1; }
int sparseExample(char *fname,unsigned long fname_len) { SciErr sciErr; int* piAddr = NULL; int iType = 0; int iRet = 0; CheckInputArgument(pvApiCtx, 1, 1); CheckOutputArgument(pvApiCtx, 0, 1); sciErr = getVarAddressFromPosition(pvApiCtx, 1, &piAddr); if(sciErr.iErr) { printError(&sciErr, 0); return 0; } if(isSparseType(pvApiCtx, piAddr)) { int iRows = 0; int iCols = 0; int iNbItem = 0; int* piNbItemRow = NULL; int* piColPos = NULL; double* pdblReal = NULL; double* pdblImg = NULL; if(isVarComplex(pvApiCtx, piAddr)) { iRet = getAllocatedComplexSparseMatrix(pvApiCtx, piAddr, &iRows, &iCols, &iNbItem, &piNbItemRow, &piColPos, &pdblReal, &pdblImg); if(iRet) { freeAllocatedComplexSparseMatrix(piNbItemRow, piColPos, pdblReal, pdblImg); return iRet; } sciErr = createComplexSparseMatrix(pvApiCtx, InputArgument + 1, iRows, iCols, iNbItem, piNbItemRow, piColPos, pdblReal, pdblImg); if(sciErr.iErr) { freeAllocatedComplexSparseMatrix(piNbItemRow, piColPos, pdblReal, pdblImg); printError(&sciErr, 0); return sciErr.iErr; } freeAllocatedComplexSparseMatrix(piNbItemRow, piColPos, pdblReal, pdblImg); } else { iRet = getAllocatedSparseMatrix(pvApiCtx, piAddr, &iRows, &iCols, &iNbItem, &piNbItemRow, &piColPos, &pdblReal); if(iRet) { freeAllocatedSparseMatrix(piNbItemRow, piColPos, pdblReal); return iRet; } sciErr = createSparseMatrix(pvApiCtx, InputArgument + 1, iRows, iCols, iNbItem, piNbItemRow, piColPos, pdblReal); if(sciErr.iErr) { freeAllocatedSparseMatrix(piNbItemRow, piColPos, pdblReal); printError(&sciErr, 0); return sciErr.iErr; } freeAllocatedSparseMatrix(piNbItemRow, piColPos, pdblReal); } AssignOutputVariable(1) = InputArgument + 1; } else { AssignOutputVariable(1) = 0; } return 0; }
//*************************************************************************************************************** int Bellerophon::driverChimeras(vector<int> midpoints, linePair line) { try { for (int h = line.start; h < (line.start + line.num); h++) { count = h; int midpoint = midpoints[h]; //initialize pref[count] for (int i = 0; i < numSeqs; i++ ) { pref[count][i].name = seqs[i]->getName(); pref[count][i].midpoint = midpoint; } if (m->control_pressed) { return 0; } //create 2 vectors of sequences, 1 for left side and one for right side vector<Sequence> left; vector<Sequence> right; for (int i = 0; i < seqs.size(); i++) { if (m->control_pressed) { return 0; } //cout << "midpoint = " << midpoint << "\twindow = " << window << endl; //cout << "whole = " << seqs[i]->getAligned().length() << endl; //save left side string seqLeft = seqs[i]->getAligned().substr(midpoint-window, window); Sequence tempLeft; tempLeft.setName(seqs[i]->getName()); tempLeft.setAligned(seqLeft); left.push_back(tempLeft); //cout << "left = " << tempLeft.getAligned().length() << endl; //save right side string seqRight = seqs[i]->getAligned().substr(midpoint, window); Sequence tempRight; tempRight.setName(seqs[i]->getName()); tempRight.setAligned(seqRight); right.push_back(tempRight); //cout << "right = " << seqRight.length() << endl; } //this should be parallelized //perference = sum of (| distance of my left to sequence j's left - distance of my right to sequence j's right | ) //create a matrix containing the distance from left to left and right to right //calculate distances SparseMatrix* SparseLeft = new SparseMatrix(); SparseMatrix* SparseRight = new SparseMatrix(); createSparseMatrix(0, left.size(), SparseLeft, left); if (m->control_pressed) { delete SparseLeft; delete SparseRight; return 0; } createSparseMatrix(0, right.size(), SparseRight, right); if (m->control_pressed) { delete SparseLeft; delete SparseRight; return 0; } left.clear(); right.clear(); vector<SeqMap> distMapRight; vector<SeqMap> distMapLeft; // Create a data structure to quickly access the distance information. //this is from thallingers reimplementation on get.oturep // It consists of a vector of distance maps, where each map contains // all distances of a certain sequence. Vector and maps are accessed // via the index of a sequence in the distance matrix distMapRight = vector<SeqMap>(numSeqs); distMapLeft = vector<SeqMap>(numSeqs); //cout << "left" << endl << endl; for (MatData currentCell = SparseLeft->begin(); currentCell != SparseLeft->end(); currentCell++) { distMapLeft[currentCell->row][currentCell->column] = currentCell->dist; if (m->control_pressed) { delete SparseLeft; delete SparseRight; return 0; } //cout << " i = " << currentCell->row << " j = " << currentCell->column << " dist = " << currentCell->dist << endl; } //cout << "right" << endl << endl; for (MatData currentCell = SparseRight->begin(); currentCell != SparseRight->end(); currentCell++) { distMapRight[currentCell->row][currentCell->column] = currentCell->dist; if (m->control_pressed) { delete SparseLeft; delete SparseRight; return 0; } //cout << " i = " << currentCell->row << " j = " << currentCell->column << " dist = " << currentCell->dist << endl; } delete SparseLeft; delete SparseRight; //fill preference structure generatePreferences(distMapLeft, distMapRight, midpoint); if (m->control_pressed) { return 0; } //report progress if((h+1) % 10 == 0){ cout << "Processing sliding window: " << toString(h+1) << "\n"; m->mothurOutJustToLog("Processing sliding window: " + toString(h+1) + "\n") ; } } //report progress if((line.start + line.num) % 10 != 0){ cout << "Processing sliding window: " << toString(line.start + line.num) << "\n"; m->mothurOutJustToLog("Processing sliding window: " + toString(line.start + line.num) + "\n") ; } return 0; } catch(exception& e) { m->errorOut(e, "Bellerophon", "driverChimeras"); exit(1); } }