CoinUtils
trunk
|
00001 /* $Id$ */ 00002 // Copyright (C) 2002, International Business Machines 00003 // Corporation and others. All Rights Reserved. 00004 // This code is licensed under the terms of the Eclipse Public License (EPL). 00005 00006 #ifndef CoinPresolveMatrix_H 00007 #define CoinPresolveMatrix_H 00008 00009 #include "CoinPragma.hpp" 00010 #include "CoinPackedMatrix.hpp" 00011 #include "CoinMessage.hpp" 00012 #include "CoinTime.hpp" 00013 00014 #include <cmath> 00015 #include <cassert> 00016 #include <cfloat> 00017 #include <cassert> 00018 #include <cstdlib> 00019 00020 #if PRESOLVE_DEBUG > 0 00021 #include "CoinFinite.hpp" 00022 #endif 00023 00032 #if defined(_MSC_VER) 00033 // Avoid MS Compiler problem in recognizing type to delete 00034 // by casting to type. 00035 // Is this still necessary? -- lh, 111202 -- 00036 #define deleteAction(array,type) delete [] ((type) array) 00037 #else 00038 #define deleteAction(array,type) delete [] array 00039 #endif 00040 00041 /* 00042 Define PRESOLVE_DEBUG and PRESOLVE_CONSISTENCY on the configure command 00043 line or in a Makefile! See comments in CoinPresolvePsdebug.hpp. 00044 */ 00045 #if PRESOLVE_DEBUG > 0 || PRESOLVE_CONSISTENCY > 0 00046 00047 #define PRESOLVE_STMT(s) s 00048 00049 #define PRESOLVEASSERT(x) \ 00050 ((x) ? 1 : ((std::cerr << "FAILED ASSERTION at line " \ 00051 << __LINE__ << ": " #x "\n"), abort(), 0)) 00052 00053 inline void DIE(const char *s) { std::cout << s ; abort() ; } 00054 00065 #define PRESENT_IN_REDUCED '\377' 00066 00067 #else 00068 00069 #define PRESOLVEASSERT(x) {} 00070 #define PRESOLVE_STMT(s) {} 00071 00072 inline void DIE(const char *) {} 00073 00074 #endif 00075 00076 /* 00077 Unclear why these are separate from standard debug. 00078 */ 00079 #ifndef PRESOLVE_DETAIL 00080 #define PRESOLVE_DETAIL_PRINT(s) {} 00081 #else 00082 #define PRESOLVE_DETAIL_PRINT(s) s 00083 #endif 00084 00089 const double ZTOLDP = 1e-12 ; 00094 const double ZTOLDP2 = 1e-10 ; 00095 00097 #define PRESOLVE_INF COIN_DBL_MAX 00098 00099 #define PRESOLVE_SMALL_INF 1.0e20 00100 00101 #define PRESOLVEFINITE(n) (-PRESOLVE_INF < (n) && (n) < PRESOLVE_INF) 00102 00103 00104 class CoinPostsolveMatrix ; 00105 00155 class CoinPresolveAction 00156 { 00157 public: 00164 static void throwCoinError(const char *error, const char *ps_routine) 00165 { throw CoinError(error, ps_routine, "CoinPresolve"); } 00166 00171 const CoinPresolveAction *next; 00172 00178 CoinPresolveAction(const CoinPresolveAction *next) : next(next) {} 00180 inline void setNext(const CoinPresolveAction *nextAction) 00181 { next = nextAction;} 00182 00187 virtual const char *name() const = 0; 00188 00192 virtual void postsolve(CoinPostsolveMatrix *prob) const = 0; 00193 00195 virtual ~CoinPresolveAction() {} 00196 }; 00197 00198 /* 00199 These are needed for OSI-aware constructors associated with 00200 CoinPrePostsolveMatrix, CoinPresolveMatrix, and CoinPostsolveMatrix. 00201 */ 00202 class ClpSimplex; 00203 class OsiSolverInterface; 00204 00205 /* 00206 CoinWarmStartBasis is required for methods in CoinPrePostsolveMatrix 00207 that accept/return a CoinWarmStartBasis object. 00208 */ 00209 class CoinWarmStartBasis ; 00210 00265 class CoinPrePostsolveMatrix 00266 { 00267 public: 00268 00278 CoinPrePostsolveMatrix(int ncols_alloc, int nrows_alloc, 00279 CoinBigIndex nelems_alloc) ; 00280 00285 CoinPrePostsolveMatrix(const OsiSolverInterface * si, 00286 int ncols_, 00287 int nrows_, 00288 CoinBigIndex nelems_); 00289 00294 CoinPrePostsolveMatrix(const ClpSimplex * si, 00295 int ncols_, 00296 int nrows_, 00297 CoinBigIndex nelems_, 00298 double bulkRatio); 00299 00301 ~CoinPrePostsolveMatrix(); 00303 00313 enum Status { 00314 isFree = 0x00, 00315 basic = 0x01, 00316 atUpperBound = 0x02, 00317 atLowerBound = 0x03, 00318 superBasic = 0x04 00319 }; 00320 00333 00335 inline void setRowStatus(int sequence, Status status) 00336 { 00337 unsigned char & st_byte = rowstat_[sequence]; 00338 st_byte = static_cast<unsigned char>(st_byte & (~7)) ; 00339 st_byte = static_cast<unsigned char>(st_byte | status) ; 00340 } 00342 inline Status getRowStatus(int sequence) const 00343 {return static_cast<Status> (rowstat_[sequence]&7);} 00345 inline bool rowIsBasic(int sequence) const 00346 {return (static_cast<Status> (rowstat_[sequence]&7)==basic);} 00348 inline void setColumnStatus(int sequence, Status status) 00349 { 00350 unsigned char & st_byte = colstat_[sequence]; 00351 st_byte = static_cast<unsigned char>(st_byte & (~7)) ; 00352 st_byte = static_cast<unsigned char>(st_byte | status) ; 00353 00354 # ifdef PRESOLVE_DEBUG 00355 switch (status) 00356 { case isFree: 00357 { if (clo_[sequence] > -PRESOLVE_INF || cup_[sequence] < PRESOLVE_INF) 00358 { std::cout << "Bad status: Var " << sequence 00359 << " isFree, lb = " << clo_[sequence] 00360 << ", ub = " << cup_[sequence] << std::endl ; } 00361 break ; } 00362 case basic: 00363 { break ; } 00364 case atUpperBound: 00365 { if (cup_[sequence] >= PRESOLVE_INF) 00366 { std::cout << "Bad status: Var " << sequence 00367 << " atUpperBound, lb = " << clo_[sequence] 00368 << ", ub = " << cup_[sequence] << std::endl ; } 00369 break ; } 00370 case atLowerBound: 00371 { if (clo_[sequence] <= -PRESOLVE_INF) 00372 { std::cout << "Bad status: Var " << sequence 00373 << " atLowerBound, lb = " << clo_[sequence] 00374 << ", ub = " << cup_[sequence] << std::endl ; } 00375 break ; } 00376 case superBasic: 00377 { if (clo_[sequence] <= -PRESOLVE_INF && cup_[sequence] >= PRESOLVE_INF) 00378 { std::cout << "Bad status: Var " << sequence 00379 << " superBasic, lb = " << clo_[sequence] 00380 << ", ub = " << cup_[sequence] << std::endl ; } 00381 break ; } 00382 default: 00383 { assert(false) ; 00384 break ; } } 00385 # endif 00386 } 00388 inline Status getColumnStatus(int sequence) const 00389 {return static_cast<Status> (colstat_[sequence]&7);} 00391 inline bool columnIsBasic(int sequence) const 00392 {return (static_cast<Status> (colstat_[sequence]&7)==basic);} 00396 void setRowStatusUsingValue(int iRow); 00400 void setColumnStatusUsingValue(int iColumn); 00402 void setStructuralStatus(const char *strucStatus, int lenParam) ; 00404 void setArtificialStatus(const char *artifStatus, int lenParam) ; 00406 void setStatus(const CoinWarmStartBasis *basis) ; 00408 CoinWarmStartBasis *getStatus() ; 00412 const char *columnStatusString(int j) const ; 00416 const char *rowStatusString(int i) const ; 00418 00426 00427 void setObjOffset(double offset) ; 00434 void setObjSense(double objSense) ; 00436 void setPrimalTolerance(double primTol) ; 00438 void setDualTolerance(double dualTol) ; 00440 void setColLower(const double *colLower, int lenParam) ; 00442 void setColUpper(const double *colUpper, int lenParam) ; 00444 void setColSolution(const double *colSol, int lenParam) ; 00446 void setCost(const double *cost, int lenParam) ; 00448 void setReducedCost(const double *redCost, int lenParam) ; 00450 void setRowLower(const double *rowLower, int lenParam) ; 00452 void setRowUpper(const double *rowUpper, int lenParam) ; 00454 void setRowPrice(const double *rowSol, int lenParam) ; 00456 void setRowActivity(const double *rowAct, int lenParam) ; 00458 00461 00462 inline int getNumCols() const 00463 { return (ncols_) ; } 00465 inline int getNumRows() const 00466 { return (nrows_) ; } 00468 inline int getNumElems() const 00469 { return (nelems_) ; } 00471 inline const CoinBigIndex *getColStarts() const 00472 { return (mcstrt_) ; } 00474 inline const int *getColLengths() const 00475 { return (hincol_) ; } 00477 inline const int *getRowIndicesByCol() const 00478 { return (hrow_) ; } 00480 inline const double *getElementsByCol() const 00481 { return (colels_) ; } 00483 inline const double *getColLower() const 00484 { return (clo_) ; } 00486 inline const double *getColUpper() const 00487 { return (cup_) ; } 00489 inline const double *getCost() const 00490 { return (cost_) ; } 00492 inline const double *getRowLower() const 00493 { return (rlo_) ; } 00495 inline const double *getRowUpper() const 00496 { return (rup_) ; } 00498 inline const double *getColSolution() const 00499 { return (sol_) ; } 00501 inline const double *getRowActivity() const 00502 { return (acts_) ; } 00504 inline const double *getRowPrice() const 00505 { return (rowduals_) ; } 00507 inline const double *getReducedCost() const 00508 { return (rcosts_) ; } 00510 inline int countEmptyCols() 00511 { int empty = 0 ; 00512 for (int i = 0 ; i < ncols_ ; i++) if (hincol_[i] == 0) empty++ ; 00513 return (empty) ; } 00515 00516 00519 00520 inline CoinMessageHandler *messageHandler() const 00521 { return handler_; } 00527 inline void setMessageHandler(CoinMessageHandler *handler) 00528 { if (defaultHandler_ == true) 00529 { delete handler_ ; 00530 defaultHandler_ = false ; } 00531 handler_ = handler ; } 00533 inline CoinMessages messages() const 00534 { return messages_; } 00536 00546 00548 int ncols_; 00550 int nrows_; 00552 CoinBigIndex nelems_; 00553 00555 int ncols0_; 00557 int nrows0_ ; 00559 CoinBigIndex nelems0_ ; 00568 CoinBigIndex bulk0_ ; 00570 double bulkRatio_; 00572 00581 00582 CoinBigIndex *mcstrt_; 00584 int *hincol_; 00586 int *hrow_; 00588 double *colels_; 00589 00591 double *cost_; 00593 double originalOffset_; 00594 00596 double *clo_; 00598 double *cup_; 00599 00601 double *rlo_; 00603 double *rup_; 00604 00611 int * originalColumn_; 00618 int * originalRow_; 00619 00621 double ztolzb_; 00623 double ztoldj_; 00624 00630 double maxmin_; 00632 00653 double *sol_; 00659 double *rowduals_; 00665 double *acts_; 00671 double *rcosts_; 00672 00679 unsigned char *colstat_; 00680 00687 unsigned char *rowstat_; 00689 00698 00699 CoinMessageHandler *handler_; 00701 bool defaultHandler_; 00703 CoinMessage messages_; 00705 00706 }; 00707 00711 const char *statusName (CoinPrePostsolveMatrix::Status status) ; 00712 00713 00738 class presolvehlink 00739 { public: 00740 int pre, suc; 00741 } ; 00742 00743 #define NO_LINK -66666666 00744 00750 inline void PRESOLVE_REMOVE_LINK(presolvehlink *link, int i) 00751 { 00752 int ipre = link[i].pre; 00753 int isuc = link[i].suc; 00754 if (ipre >= 0) { 00755 link[ipre].suc = isuc; 00756 } 00757 if (isuc >= 0) { 00758 link[isuc].pre = ipre; 00759 } 00760 link[i].pre = NO_LINK, link[i].suc = NO_LINK; 00761 } 00762 00768 inline void PRESOLVE_INSERT_LINK(presolvehlink *link, int i, int j) 00769 { 00770 int isuc = link[j].suc; 00771 link[j].suc = i; 00772 link[i].pre = j; 00773 if (isuc >= 0) { 00774 link[isuc].pre = i; 00775 } 00776 link[i].suc = isuc; 00777 } 00778 00790 inline void PRESOLVE_MOVE_LINK(presolvehlink *link, int i, int j) 00791 { 00792 int ipre = link[i].pre; 00793 int isuc = link[i].suc; 00794 if (ipre >= 0) { 00795 link[ipre].suc = j; 00796 } 00797 if (isuc >= 0) { 00798 link[isuc].pre = j; 00799 } 00800 link[i].pre = NO_LINK, link[i].suc = NO_LINK; 00801 } 00802 00803 00835 class CoinPresolveMatrix : public CoinPrePostsolveMatrix 00836 { 00837 public: 00838 00845 CoinPresolveMatrix(int ncols_alloc, int nrows_alloc, 00846 CoinBigIndex nelems_alloc) ; 00847 00852 CoinPresolveMatrix(int ncols0, 00853 double maxmin, 00854 // end prepost members 00855 00856 ClpSimplex * si, 00857 00858 // rowrep 00859 int nrows, 00860 CoinBigIndex nelems, 00861 bool doStatus, 00862 double nonLinearVariable, 00863 double bulkRatio); 00864 00866 void update_model(ClpSimplex * si, 00867 int nrows0, 00868 int ncols0, 00869 CoinBigIndex nelems0); 00874 CoinPresolveMatrix(int ncols0, 00875 double maxmin, 00876 // end prepost members 00877 OsiSolverInterface * si, 00878 // rowrep 00879 int nrows, 00880 CoinBigIndex nelems, 00881 bool doStatus, 00882 double nonLinearVariable, 00883 const char * prohibited, 00884 const char * rowProhibited=NULL); 00885 00887 void update_model(OsiSolverInterface * si, 00888 int nrows0, 00889 int ncols0, 00890 CoinBigIndex nelems0); 00891 00893 ~CoinPresolveMatrix(); 00894 00900 friend void assignPresolveToPostsolve (CoinPresolveMatrix *&preObj) ; 00901 00910 void setMatrix(const CoinPackedMatrix *mtx) ; 00911 00913 inline int countEmptyRows() 00914 { int empty = 0 ; 00915 for (int i = 0 ; i < nrows_ ; i++) if (hinrow_[i] == 0) empty++ ; 00916 return (empty) ; } 00917 00923 inline void setVariableType(int i, int variableType) 00924 { if (integerType_ == 0) integerType_ = new unsigned char [ncols0_] ; 00925 integerType_[i] = static_cast<unsigned char>(variableType) ; } 00926 00932 void setVariableType(const unsigned char *variableType, int lenParam) ; 00933 00939 void setVariableType (bool allIntegers, int lenParam) ; 00940 00942 inline void setAnyInteger (bool anyInteger = true) 00943 { anyInteger_ = anyInteger ; } 00945 00949 00951 inline const CoinBigIndex *getRowStarts() const 00952 { return (mrstrt_) ; } 00954 inline const int *getColIndicesByRow() const 00955 { return (hcol_) ; } 00957 inline const double *getElementsByRow() const 00958 { return (rowels_) ; } 00959 00965 inline bool isInteger (int i) const 00966 { if (integerType_ == 0) 00967 { return (anyInteger_) ; } 00968 else 00969 if (integerType_[i] == 1) 00970 { return (true) ; } 00971 else 00972 { return (false) ; } } 00973 00978 inline bool anyInteger () const 00979 { return (anyInteger_) ; } 00981 inline int presolveOptions() const 00982 { return presolveOptions_;} 00984 inline void setPresolveOptions(int value) 00985 { presolveOptions_=value;} 00987 00995 00996 presolvehlink *clink_; 00998 presolvehlink *rlink_; 01000 01002 double dobias_ ; 01003 01005 inline void change_bias(double change_amount) 01006 { 01007 dobias_ += change_amount ; 01008 # if PRESOLVE_DEBUG > 2 01009 assert(fabs(change_amount)<1.0e50) ; 01010 if (change_amount) 01011 PRESOLVE_STMT(printf("changing bias by %g to %g\n", 01012 change_amount, dobias_)) ; 01013 # endif 01014 } 01015 01024 01025 CoinBigIndex *mrstrt_; 01027 int *hinrow_; 01029 double *rowels_; 01031 int *hcol_; 01033 01035 unsigned char *integerType_; 01041 bool anyInteger_ ; 01043 bool tuning_; 01045 void statistics(); 01047 double startTime_; 01048 01050 double feasibilityTolerance_; 01052 inline double feasibilityTolerance() 01053 { return (feasibilityTolerance_) ; } 01055 inline void setFeasibilityTolerance (double val) 01056 { feasibilityTolerance_ = val ; } 01057 01063 int status_; 01065 inline int status() 01066 { return (status_) ; } 01068 inline void setStatus(int status) 01069 { status_ = (status&0x3) ; } 01070 01078 int pass_; 01080 inline void setPass (int pass = 0) 01081 { pass_ = pass ; } 01082 01087 int maxSubstLevel_; 01089 inline void setMaximumSubstitutionLevel (int level) 01090 { maxSubstLevel_ = level ; } 01091 01092 01116 unsigned char * colChanged_; 01118 int * colsToDo_; 01120 int numberColsToDo_; 01122 int * nextColsToDo_; 01124 int numberNextColsToDo_; 01125 01135 unsigned char * rowChanged_; 01137 int * rowsToDo_; 01139 int numberRowsToDo_; 01141 int * nextRowsToDo_; 01143 int numberNextRowsToDo_; 01161 int presolveOptions_; 01167 bool anyProhibited_; 01169 01180 01181 int *usefulRowInt_ ; 01183 double *usefulRowDouble_ ; 01185 int *usefulColumnInt_ ; 01187 double *usefulColumnDouble_ ; 01189 double *randomNumber_ ; 01190 01192 int *infiniteUp_ ; 01194 double *sumUp_ ; 01196 int *infiniteDown_ ; 01198 double *sumDown_ ; 01200 01212 int recomputeSums(int whichRow) ; 01213 01215 void initializeStuff() ; 01217 void deleteStuff() ; 01218 01221 01227 void initColsToDo () ; 01228 01234 int stepColsToDo () ; 01235 01237 inline int numberColsToDo() 01238 { return (numberColsToDo_) ; } 01239 01241 inline bool colChanged(int i) const { 01242 return (colChanged_[i]&1)!=0; 01243 } 01245 inline void unsetColChanged(int i) { 01246 colChanged_[i] = static_cast<unsigned char>(colChanged_[i] & (~1)) ; 01247 } 01249 inline void setColChanged(int i) { 01250 colChanged_[i] = static_cast<unsigned char>(colChanged_[i] | (1)) ; 01251 } 01253 inline void addCol(int i) { 01254 if ((colChanged_[i]&1)==0) { 01255 colChanged_[i] = static_cast<unsigned char>(colChanged_[i] | (1)) ; 01256 nextColsToDo_[numberNextColsToDo_++] = i; 01257 } 01258 } 01260 inline bool colProhibited(int i) const { 01261 return (colChanged_[i]&2)!=0; 01262 } 01269 inline bool colProhibited2(int i) const { 01270 if (!anyProhibited_) 01271 return false; 01272 else 01273 return (colChanged_[i]&2)!=0; 01274 } 01276 inline void setColProhibited(int i) { 01277 colChanged_[i] = static_cast<unsigned char>(colChanged_[i] | (2)) ; 01278 } 01284 inline bool colUsed(int i) const { 01285 return (colChanged_[i]&4)!=0; 01286 } 01288 inline void setColUsed(int i) { 01289 colChanged_[i] = static_cast<unsigned char>(colChanged_[i] | (4)) ; 01290 } 01292 inline void unsetColUsed(int i) { 01293 colChanged_[i] = static_cast<unsigned char>(colChanged_[i] & (~4)) ; 01294 } 01296 inline bool colInfinite(int i) const { 01297 return (colChanged_[i]&8)!=0; 01298 } 01300 inline void unsetColInfinite(int i) { 01301 colChanged_[i] = static_cast<unsigned char>(colChanged_[i] & (~8)) ; 01302 } 01304 inline void setColInfinite(int i) { 01305 colChanged_[i] = static_cast<unsigned char>(colChanged_[i] | (8)) ; 01306 } 01307 01313 void initRowsToDo () ; 01314 01320 int stepRowsToDo () ; 01321 01323 inline int numberRowsToDo() 01324 { return (numberRowsToDo_) ; } 01325 01327 inline bool rowChanged(int i) const { 01328 return (rowChanged_[i]&1)!=0; 01329 } 01331 inline void unsetRowChanged(int i) { 01332 rowChanged_[i] = static_cast<unsigned char>(rowChanged_[i] & (~1)) ; 01333 } 01335 inline void setRowChanged(int i) { 01336 rowChanged_[i] = static_cast<unsigned char>(rowChanged_[i] | (1)) ; 01337 } 01339 inline void addRow(int i) { 01340 if ((rowChanged_[i]&1)==0) { 01341 rowChanged_[i] = static_cast<unsigned char>(rowChanged_[i] | (1)) ; 01342 nextRowsToDo_[numberNextRowsToDo_++] = i; 01343 } 01344 } 01346 inline bool rowProhibited(int i) const { 01347 return (rowChanged_[i]&2)!=0; 01348 } 01355 inline bool rowProhibited2(int i) const { 01356 if (!anyProhibited_) 01357 return false; 01358 else 01359 return (rowChanged_[i]&2)!=0; 01360 } 01362 inline void setRowProhibited(int i) { 01363 rowChanged_[i] = static_cast<unsigned char>(rowChanged_[i] | (2)) ; 01364 } 01370 inline bool rowUsed(int i) const { 01371 return (rowChanged_[i]&4)!=0; 01372 } 01374 inline void setRowUsed(int i) { 01375 rowChanged_[i] = static_cast<unsigned char>(rowChanged_[i] | (4)) ; 01376 } 01378 inline void unsetRowUsed(int i) { 01379 rowChanged_[i] = static_cast<unsigned char>(rowChanged_[i] & (~4)) ; 01380 } 01381 01382 01384 inline bool anyProhibited() const 01385 { return anyProhibited_;} 01387 inline void setAnyProhibited(bool val = true) 01388 { anyProhibited_ = val ; } 01390 01391 }; 01392 01421 class CoinPostsolveMatrix : public CoinPrePostsolveMatrix 01422 { 01423 public: 01424 01431 CoinPostsolveMatrix(int ncols_alloc, int nrows_alloc, 01432 CoinBigIndex nelems_alloc) ; 01433 01434 01439 CoinPostsolveMatrix(ClpSimplex * si, 01440 01441 int ncols0, 01442 int nrows0, 01443 CoinBigIndex nelems0, 01444 01445 double maxmin_, 01446 // end prepost members 01447 01448 double *sol, 01449 double *acts, 01450 01451 unsigned char *colstat, 01452 unsigned char *rowstat); 01453 01458 CoinPostsolveMatrix(OsiSolverInterface * si, 01459 01460 int ncols0, 01461 int nrows0, 01462 CoinBigIndex nelems0, 01463 01464 double maxmin_, 01465 // end prepost members 01466 01467 double *sol, 01468 double *acts, 01469 01470 unsigned char *colstat, 01471 unsigned char *rowstat); 01472 01483 void assignPresolveToPostsolve (CoinPresolveMatrix *&preObj) ; 01484 01486 ~CoinPostsolveMatrix(); 01487 01499 01501 CoinBigIndex free_list_; 01503 int maxlink_; 01508 CoinBigIndex *link_; 01509 01511 01519 char *cdone_; 01520 char *rdone_; 01522 01524 void check_nbasic(); 01525 01526 }; 01527 01528 01535 01540 void presolve_make_memlists(/*CoinBigIndex *starts,*/ int *lengths, 01541 presolvehlink *link, int n); 01542 01550 bool presolve_expand_major(CoinBigIndex *majstrts, double *majels, 01551 int *minndxs, int *majlens, 01552 presolvehlink *majlinks, int nmaj, int k) ; 01553 01559 inline bool presolve_expand_col(CoinBigIndex *mcstrt, double *colels, 01560 int *hrow, int *hincol, 01561 presolvehlink *clink, int ncols, int colx) 01562 { return presolve_expand_major(mcstrt,colels, 01563 hrow,hincol,clink,ncols,colx) ; } 01564 01570 inline bool presolve_expand_row(CoinBigIndex *mrstrt, double *rowels, 01571 int *hcol, int *hinrow, 01572 presolvehlink *rlink, int nrows, int rowx) 01573 { return presolve_expand_major(mrstrt,rowels, 01574 hcol,hinrow,rlink,nrows,rowx) ; } 01575 01576 01585 inline CoinBigIndex presolve_find_minor(int tgt, 01586 CoinBigIndex ks, CoinBigIndex ke, 01587 const int *minndxs) 01588 { CoinBigIndex k ; 01589 for (k = ks ; k < ke ; k++) 01590 #ifndef NDEBUG 01591 { if (minndxs[k] == tgt) 01592 return (k) ; } 01593 DIE("FIND_MINOR") ; 01594 01595 abort () ; return -1; 01596 #else 01597 { if (minndxs[k] == tgt) 01598 break ; } 01599 return (k) ; 01600 #endif 01601 } 01602 01609 inline CoinBigIndex presolve_find_row(int row, CoinBigIndex kcs, 01610 CoinBigIndex kce, const int *hrow) 01611 { return presolve_find_minor(row,kcs,kce,hrow) ; } 01612 01619 inline CoinBigIndex presolve_find_col(int col, CoinBigIndex krs, 01620 CoinBigIndex kre, const int *hcol) 01621 { return presolve_find_minor(col,krs,kre,hcol) ; } 01622 01623 01632 CoinBigIndex presolve_find_minor1(int tgt, CoinBigIndex ks, CoinBigIndex ke, 01633 const int *minndxs); 01634 01641 inline CoinBigIndex presolve_find_row1(int row, CoinBigIndex kcs, 01642 CoinBigIndex kce, const int *hrow) 01643 { return presolve_find_minor1(row,kcs,kce,hrow) ; } 01644 01651 inline CoinBigIndex presolve_find_col1(int col, CoinBigIndex krs, 01652 CoinBigIndex kre, const int *hcol) 01653 { return presolve_find_minor1(col,krs,kre,hcol) ; } 01654 01663 CoinBigIndex presolve_find_minor2(int tgt, CoinBigIndex ks, int majlen, 01664 const int *minndxs, 01665 const CoinBigIndex *majlinks) ; 01666 01674 inline CoinBigIndex presolve_find_row2(int row, CoinBigIndex kcs, int collen, 01675 const int *hrow, 01676 const CoinBigIndex *clinks) 01677 { return presolve_find_minor2(row,kcs,collen,hrow,clinks) ; } 01678 01687 CoinBigIndex presolve_find_minor3(int tgt, CoinBigIndex ks, int majlen, 01688 const int *minndxs, 01689 const CoinBigIndex *majlinks) ; 01690 01698 inline CoinBigIndex presolve_find_row3(int row, CoinBigIndex kcs, int collen, 01699 const int *hrow, 01700 const CoinBigIndex *clinks) 01701 { return presolve_find_minor3(row,kcs,collen,hrow,clinks) ; } 01702 01712 inline void presolve_delete_from_major(int majndx, int minndx, 01713 const CoinBigIndex *majstrts, 01714 int *majlens, int *minndxs, double *els) 01715 { 01716 const CoinBigIndex ks = majstrts[majndx] ; 01717 const CoinBigIndex ke = ks+majlens[majndx] ; 01718 01719 const CoinBigIndex kmi = presolve_find_minor(minndx,ks,ke,minndxs) ; 01720 01721 minndxs[kmi] = minndxs[ke-1] ; 01722 els[kmi] = els[ke-1] ; 01723 majlens[majndx]-- ; 01724 01725 return ; 01726 } 01727 01734 inline void presolve_delete_many_from_major(int majndx, char *marked, 01735 const CoinBigIndex *majstrts, 01736 int *majlens, int *minndxs, double *els) 01737 { 01738 const CoinBigIndex ks = majstrts[majndx] ; 01739 const CoinBigIndex ke = ks+majlens[majndx] ; 01740 CoinBigIndex put = ks ; 01741 for (CoinBigIndex k = ks ; k < ke ; k++) { 01742 int iMinor = minndxs[k] ; 01743 if (!marked[iMinor]) { 01744 minndxs[put] = iMinor ; 01745 els[put++] = els[k] ; 01746 } else { 01747 marked[iMinor] = 0 ; 01748 } 01749 } 01750 majlens[majndx] = put-ks ; 01751 return ; 01752 } 01753 01764 inline void presolve_delete_from_col(int row, int col, 01765 const CoinBigIndex *mcstrt, 01766 int *hincol, int *hrow, double *colels) 01767 { presolve_delete_from_major(col,row,mcstrt,hincol,hrow,colels) ; } 01768 01779 inline void presolve_delete_from_row(int row, int col, 01780 const CoinBigIndex *mrstrt, 01781 int *hinrow, int *hcol, double *rowels) 01782 { presolve_delete_from_major(row,col,mrstrt,hinrow,hcol,rowels) ; } 01783 01794 void presolve_delete_from_major2 (int majndx, int minndx, 01795 CoinBigIndex *majstrts, int *majlens, 01796 int *minndxs, int *majlinks, 01797 CoinBigIndex *free_listp) ; 01798 01809 inline void presolve_delete_from_col2(int row, int col, CoinBigIndex *mcstrt, 01810 int *hincol, int *hrow, 01811 int *clinks, CoinBigIndex *free_listp) 01812 { presolve_delete_from_major2(col,row,mcstrt,hincol,hrow,clinks,free_listp) ; } 01813 01815 01821 01833 double *presolve_dupmajor(const double *elems, const int *indices, 01834 int length, CoinBigIndex offset, int tgt = -1); 01835 01837 void coin_init_random_vec(double *work, int n); 01838 01840 01841 01842 #endif