38d596cb81
* Added Jamfile by James Kim and Christof Lutteroth. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@23888 a95241bf-73f2-0310-859d-f6bbb57e9c96
258 lines
12 KiB
C
258 lines
12 KiB
C
#ifndef HEADER_lp_matrix
|
|
#define HEADER_lp_matrix
|
|
|
|
#include "lp_types.h"
|
|
#include "lp_utils.h"
|
|
|
|
|
|
/* Sparse matrix element (ordered columnwise) */
|
|
typedef struct _MATitem
|
|
{
|
|
int rownr;
|
|
int colnr;
|
|
REAL value;
|
|
} MATitem;
|
|
|
|
/* Constants for matrix product rounding options */
|
|
#define MAT_ROUNDNONE 0
|
|
#define MAT_ROUNDABS 1
|
|
#define MAT_ROUNDREL 2
|
|
#define MAT_ROUNDABSREL (MAT_ROUNDABS + MAT_ROUNDREL)
|
|
#define MAT_ROUNDRC 4
|
|
#define MAT_ROUNDRCMIN 1.0 /* lp->epspivot */
|
|
#if 1
|
|
#define MAT_ROUNDDEFAULT MAT_ROUNDREL /* Typically increases performance */
|
|
#else
|
|
#define MAT_ROUNDDEFAULT MAT_ROUNDABS /* Probably gives more precision */
|
|
#endif
|
|
|
|
/* Compiler option development features */
|
|
/*#define DebugInv*/ /* Report array values at factorization/inversion */
|
|
#define NoLoopUnroll /* Do not do loop unrolling */
|
|
#define DirectArrayOF /* Reference lp->obj[] array instead of function call */
|
|
|
|
|
|
/* Matrix column access macros to be able to easily change storage model */
|
|
#define CAM_Record 0
|
|
#define CAM_Vector 1
|
|
#if 0
|
|
#define MatrixColAccess CAM_Record
|
|
#else
|
|
#define MatrixColAccess CAM_Vector
|
|
#endif
|
|
|
|
#if MatrixColAccess==CAM_Record
|
|
#define SET_MAT_ijA(item,i,j,A) mat->col_mat[item].rownr = i; \
|
|
mat->col_mat[item].colnr = j; \
|
|
mat->col_mat[item].value = A
|
|
#define COL_MAT_COLNR(item) (mat->col_mat[item].colnr)
|
|
#define COL_MAT_ROWNR(item) (mat->col_mat[item].rownr)
|
|
#define COL_MAT_VALUE(item) (mat->col_mat[item].value)
|
|
#define COL_MAT_COPY(left,right) mat->col_mat[left] = mat->col_mat[right]
|
|
#define COL_MAT_MOVE(to,from,rec) MEMMOVE(&(mat->col_mat[to]),&(mat->col_mat[from]),rec)
|
|
#define COL_MAT2_COLNR(item) (mat2->col_mat[item].colnr)
|
|
#define COL_MAT2_ROWNR(item) (mat2->col_mat[item].rownr)
|
|
#define COL_MAT2_VALUE(item) (mat2->col_mat[item].value)
|
|
#define matRowColStep (sizeof(MATitem)/sizeof(int))
|
|
#define matValueStep (sizeof(MATitem)/sizeof(REAL))
|
|
|
|
#else /* if MatrixColAccess==CAM_Vector */
|
|
#define SET_MAT_ijA(item,i,j,A) mat->col_mat_rownr[item] = i; \
|
|
mat->col_mat_colnr[item] = j; \
|
|
mat->col_mat_value[item] = A
|
|
#define COL_MAT_COLNR(item) (mat->col_mat_colnr[item])
|
|
#define COL_MAT_ROWNR(item) (mat->col_mat_rownr[item])
|
|
#define COL_MAT_VALUE(item) (mat->col_mat_value[item])
|
|
#define COL_MAT_COPY(left,right) COL_MAT_COLNR(left) = COL_MAT_COLNR(right); \
|
|
COL_MAT_ROWNR(left) = COL_MAT_ROWNR(right); \
|
|
COL_MAT_VALUE(left) = COL_MAT_VALUE(right)
|
|
#define COL_MAT_MOVE(to,from,rec) MEMMOVE(&COL_MAT_COLNR(to),&COL_MAT_COLNR(from),rec); \
|
|
MEMMOVE(&COL_MAT_ROWNR(to),&COL_MAT_ROWNR(from),rec); \
|
|
MEMMOVE(&COL_MAT_VALUE(to),&COL_MAT_VALUE(from),rec)
|
|
#define COL_MAT2_COLNR(item) (mat2->col_mat_colnr[item])
|
|
#define COL_MAT2_ROWNR(item) (mat2->col_mat_rownr[item])
|
|
#define COL_MAT2_VALUE(item) (mat2->col_mat_value[item])
|
|
#define matRowColStep 1
|
|
#define matValueStep 1
|
|
|
|
#endif
|
|
|
|
|
|
/* Matrix row access macros to be able to easily change storage model */
|
|
#define RAM_Index 0
|
|
#define RAM_FullCopy 1
|
|
#define MatrixRowAccess RAM_Index
|
|
|
|
#if MatrixRowAccess==RAM_Index
|
|
#define ROW_MAT_COLNR(item) COL_MAT_COLNR(mat->row_mat[item])
|
|
#define ROW_MAT_ROWNR(item) COL_MAT_ROWNR(mat->row_mat[item])
|
|
#define ROW_MAT_VALUE(item) COL_MAT_VALUE(mat->row_mat[item])
|
|
|
|
#elif MatrixColAccess==CAM_Record
|
|
#define ROW_MAT_COLNR(item) (mat->row_mat[item].colnr)
|
|
#define ROW_MAT_ROWNR(item) (mat->row_mat[item].rownr)
|
|
#define ROW_MAT_VALUE(item) (mat->row_mat[item].value)
|
|
|
|
#else /* if MatrixColAccess==CAM_Vector */
|
|
#define ROW_MAT_COLNR(item) (mat->row_mat_colnr[item])
|
|
#define ROW_MAT_ROWNR(item) (mat->row_mat_rownr[item])
|
|
#define ROW_MAT_VALUE(item) (mat->row_mat_value[item])
|
|
|
|
#endif
|
|
|
|
|
|
typedef struct _MATrec
|
|
{
|
|
/* Owner reference */
|
|
lprec *lp;
|
|
|
|
/* Active dimensions */
|
|
int rows;
|
|
int columns;
|
|
|
|
/* Allocated memory */
|
|
int rows_alloc;
|
|
int columns_alloc;
|
|
int mat_alloc; /* The allocated size for matrix sized structures */
|
|
|
|
/* Sparse problem matrix storage */
|
|
#if MatrixColAccess==CAM_Record
|
|
MATitem *col_mat; /* mat_alloc : The sparse data storage */
|
|
#else /*MatrixColAccess==CAM_Vector*/
|
|
int *col_mat_colnr;
|
|
int *col_mat_rownr;
|
|
REAL *col_mat_value;
|
|
#endif
|
|
int *col_end; /* columns_alloc+1 : col_end[i] is the index of the
|
|
first element after column i; column[i] is stored
|
|
in elements col_end[i-1] to col_end[i]-1 */
|
|
int *col_tag; /* user-definable tag associated with each column */
|
|
|
|
#if MatrixRowAccess==RAM_Index
|
|
int *row_mat; /* mat_alloc : From index 0, row_mat contains the
|
|
row-ordered index of the elements of col_mat */
|
|
#elif MatrixColAccess==CAM_Record
|
|
MATitem *row_mat; /* mat_alloc : From index 0, row_mat contains the
|
|
row-ordered copy of the elements in col_mat */
|
|
#else /*if MatrixColAccess==CAM_Vector*/
|
|
int *row_mat_colnr;
|
|
int *row_mat_rownr;
|
|
REAL *row_mat_value;
|
|
#endif
|
|
int *row_end; /* rows_alloc+1 : row_end[i] is the index of the
|
|
first element in row_mat after row i */
|
|
int *row_tag; /* user-definable tag associated with each row */
|
|
|
|
REAL *colmax; /* Array of maximum values of each column */
|
|
REAL *rowmax; /* Array of maximum values of each row */
|
|
|
|
REAL epsvalue; /* Zero element rejection threshold */
|
|
REAL infnorm; /* The largest absolute value in the matrix */
|
|
REAL dynrange;
|
|
MYBOOL row_end_valid; /* TRUE if row_end & row_mat are valid */
|
|
MYBOOL is_roworder; /* TRUE if the current (temporary) matrix order is row-wise */
|
|
|
|
} MATrec;
|
|
|
|
typedef struct _DeltaVrec
|
|
{
|
|
lprec *lp;
|
|
int activelevel;
|
|
MATrec *tracker;
|
|
} DeltaVrec;
|
|
|
|
|
|
#ifdef __cplusplus
|
|
__EXTERN_C {
|
|
#endif
|
|
|
|
/* Sparse matrix routines */
|
|
STATIC MATrec *mat_create(lprec *lp, int rows, int columns, REAL epsvalue);
|
|
STATIC MYBOOL mat_memopt(MATrec *mat, int rowextra, int colextra, int nzextra);
|
|
STATIC void mat_free(MATrec **matrix);
|
|
STATIC MYBOOL inc_matrow_space(MATrec *mat, int deltarows);
|
|
STATIC int mat_mapreplace(MATrec *mat, LLrec *rowmap, LLrec *colmap, MATrec *insmat);
|
|
STATIC int mat_matinsert(MATrec *mat, MATrec *insmat);
|
|
STATIC int mat_zerocompact(MATrec *mat);
|
|
STATIC int mat_rowcompact(MATrec *mat, MYBOOL dozeros);
|
|
STATIC int mat_colcompact(MATrec *mat, int prev_rows, int prev_cols);
|
|
STATIC MYBOOL inc_matcol_space(MATrec *mat, int deltacols);
|
|
STATIC MYBOOL inc_mat_space(MATrec *mat, int mindelta);
|
|
STATIC int mat_shiftrows(MATrec *mat, int *bbase, int delta, LLrec *varmap);
|
|
STATIC int mat_shiftcols(MATrec *mat, int *bbase, int delta, LLrec *varmap);
|
|
STATIC MATrec *mat_extractmat(MATrec *mat, LLrec *rowmap, LLrec *colmap, MYBOOL negated);
|
|
STATIC int mat_appendrow(MATrec *mat, int count, REAL *row, int *colno, REAL mult, MYBOOL checkrowmode);
|
|
STATIC int mat_appendcol(MATrec *mat, int count, REAL *column, int *rowno, REAL mult, MYBOOL checkrowmode);
|
|
MYBOOL mat_get_data(lprec *lp, int matindex, MYBOOL isrow, int **rownr, int **colnr, REAL **value);
|
|
MYBOOL mat_set_rowmap(MATrec *mat, int row_mat_index, int rownr, int colnr, int col_mat_index);
|
|
STATIC MYBOOL mat_indexrange(MATrec *mat, int index, MYBOOL isrow, int *startpos, int *endpos);
|
|
STATIC MYBOOL mat_validate(MATrec *mat);
|
|
STATIC MYBOOL mat_equalRows(MATrec *mat, int baserow, int comprow);
|
|
STATIC int mat_findelm(MATrec *mat, int row, int column);
|
|
STATIC int mat_findins(MATrec *mat, int row, int column, int *insertpos, MYBOOL validate);
|
|
STATIC void mat_multcol(MATrec *mat, int col_nr, REAL mult, MYBOOL DoObj);
|
|
STATIC REAL mat_getitem(MATrec *mat, int row, int column);
|
|
STATIC MYBOOL mat_setitem(MATrec *mat, int row, int column, REAL value);
|
|
STATIC MYBOOL mat_additem(MATrec *mat, int row, int column, REAL delta);
|
|
STATIC MYBOOL mat_setvalue(MATrec *mat, int Row, int Column, REAL Value, MYBOOL doscale);
|
|
STATIC int mat_nonzeros(MATrec *mat);
|
|
STATIC int mat_collength(MATrec *mat, int colnr);
|
|
STATIC int mat_rowlength(MATrec *mat, int rownr);
|
|
STATIC void mat_multrow(MATrec *mat, int row_nr, REAL mult);
|
|
STATIC void mat_multadd(MATrec *mat, REAL *lhsvector, int varnr, REAL mult);
|
|
STATIC MYBOOL mat_setrow(MATrec *mat, int rowno, int count, REAL *row, int *colno, MYBOOL doscale, MYBOOL checkrowmode);
|
|
STATIC MYBOOL mat_setcol(MATrec *mat, int colno, int count, REAL *column, int *rowno, MYBOOL doscale, MYBOOL checkrowmode);
|
|
STATIC MYBOOL mat_mergemat(MATrec *target, MATrec *source, MYBOOL usecolmap);
|
|
STATIC int mat_checkcounts(MATrec *mat, int *rownum, int *colnum, MYBOOL freeonexit);
|
|
STATIC int mat_expandcolumn(MATrec *mat, int colnr, REAL *column, int *nzlist, MYBOOL signedA);
|
|
STATIC MYBOOL mat_computemax(MATrec *mat);
|
|
STATIC MYBOOL mat_transpose(MATrec *mat);
|
|
|
|
/* Refactorization and recomputation routine */
|
|
MYBOOL __WINAPI invert(lprec *lp, MYBOOL shiftbounds, MYBOOL final);
|
|
|
|
/* Vector compression and expansion routines */
|
|
STATIC MYBOOL vec_compress(REAL *densevector, int startpos, int endpos, REAL epsilon, REAL *nzvector, int *nzindex);
|
|
STATIC MYBOOL vec_expand(REAL *nzvector, int *nzindex, REAL *densevector, int startpos, int endpos);
|
|
|
|
/* Sparse matrix products */
|
|
STATIC MYBOOL get_colIndexA(lprec *lp, int varset, int *colindex, MYBOOL append);
|
|
STATIC int prod_Ax(lprec *lp, int *coltarget, REAL *input, int *nzinput, REAL roundzero, REAL ofscalar, REAL *output, int *nzoutput, int roundmode);
|
|
STATIC int prod_xA(lprec *lp, int *coltarget, REAL *input, int *nzinput, REAL roundzero, REAL ofscalar, REAL *output, int *nzoutput, int roundmode);
|
|
STATIC MYBOOL prod_xA2(lprec *lp, int *coltarget, REAL *prow, REAL proundzero, int *pnzprow,
|
|
REAL *drow, REAL droundzero, int *dnzdrow, REAL ofscalar, int roundmode);
|
|
|
|
/* Equation solution */
|
|
STATIC MYBOOL fimprove(lprec *lp, REAL *pcol, int *nzidx, REAL roundzero);
|
|
STATIC void ftran(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero);
|
|
STATIC MYBOOL bimprove(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero);
|
|
STATIC void btran(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero);
|
|
|
|
/* Combined equation solution and matrix product for simplex operations */
|
|
STATIC MYBOOL fsolve(lprec *lp, int varin, REAL *pcol, int *nzidx, REAL roundzero, REAL ofscalar, MYBOOL prepareupdate);
|
|
STATIC MYBOOL bsolve(lprec *lp, int row_nr, REAL *rhsvector, int *nzidx, REAL roundzero, REAL ofscalar);
|
|
STATIC void bsolve_xA2(lprec *lp, int* coltarget,
|
|
int row_nr1, REAL *vector1, REAL roundzero1, int *nzvector1,
|
|
int row_nr2, REAL *vector2, REAL roundzero2, int *nzvector2, int roundmode);
|
|
|
|
/* Change-tracking routines (primarily for B&B and presolve) */
|
|
STATIC DeltaVrec *createUndoLadder(lprec *lp, int levelitems, int maxlevels);
|
|
STATIC int incrementUndoLadder(DeltaVrec *DV);
|
|
STATIC MYBOOL modifyUndoLadder(DeltaVrec *DV, int itemno, REAL target[], REAL newvalue);
|
|
STATIC int countsUndoLadder(DeltaVrec *DV);
|
|
STATIC int restoreUndoLadder(DeltaVrec *DV, REAL target[]);
|
|
STATIC int decrementUndoLadder(DeltaVrec *DV);
|
|
STATIC MYBOOL freeUndoLadder(DeltaVrec **DV);
|
|
|
|
/* Specialized presolve undo functions */
|
|
STATIC MYBOOL appendUndoPresolve(lprec *lp, MYBOOL isprimal, REAL beta, int colnrDep);
|
|
STATIC MYBOOL addUndoPresolve(lprec *lp, MYBOOL isprimal, int colnrElim, REAL alpha, REAL beta, int colnrDep);
|
|
|
|
|
|
#ifdef __cplusplus
|
|
}
|
|
#endif
|
|
|
|
#endif /* HEADER_lp_matrix */
|
|
|