src/lemon/lp_glpk.cc
author ladanyi
Thu, 14 Apr 2005 21:23:25 +0000
changeset 1355 57936f15055b
parent 1321 bc3a4c498eb2
child 1359 1581f961cfaa
permissions -rw-r--r--
- Use messages similar to stock autoconf macros'.
     1 /* -*- C++ -*-
     2  * src/lemon/lp_glpk.cc - Part of LEMON, a generic C++ optimization library
     3  *
     4  * Copyright (C) 2005 Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
     5  * (Egervary Combinatorial Optimization Research Group, EGRES).
     6  *
     7  * Permission to use, modify and distribute this software is granted
     8  * provided that this copyright notice appears in all copies. For
     9  * precise terms see the accompanying LICENSE file.
    10  *
    11  * This software is provided "AS IS" with no warranty of any kind,
    12  * express or implied, and with no claim as to its suitability for any
    13  * purpose.
    14  *
    15  */
    16 
    17 #ifndef LEMON_LP_GLPK_CC
    18 #define LEMON_LP_GLPK_CC
    19 
    20 ///\file
    21 ///\brief Implementation of the LEMON-GLPK lp solver interface.
    22 
    23 #include <lemon/lp_glpk.h>
    24 
    25 namespace lemon {
    26 
    27   LpGlpk::LpGlpk() : Parent(), 
    28 		     lp(lpx_create_prob()) {
    29     ///\todo constrol function for this:
    30     lpx_set_int_parm(lp, LPX_K_DUAL, 1);
    31     messageLevel(0);
    32   }
    33   
    34   LpGlpk::~LpGlpk() {
    35     lpx_delete_prob(lp);
    36   }
    37   
    38   int LpGlpk::_addCol() { 
    39     int i=lpx_add_cols(lp, 1);
    40     _setColLowerBound(i, -INF);
    41     _setColUpperBound(i, INF);
    42     return i;
    43   }
    44 
    45   int LpGlpk::_addRow() { 
    46     int i=lpx_add_rows(lp, 1);
    47     return i;
    48   }
    49 
    50   
    51   void LpGlpk::_setRowCoeffs(int i, 
    52 			     int length,
    53 			     const int   * indices, 
    54 			     const Value   * values )
    55   {
    56     lpx_set_mat_row(lp, i, length,
    57 		    const_cast<int * >(indices) ,
    58 		    const_cast<Value * >(values));
    59   }
    60   
    61   void LpGlpk::_setColCoeffs(int i, 
    62 			     int length,
    63 			     const int   * indices, 
    64 			     const Value   * values)
    65   {
    66     lpx_set_mat_col(lp, i, length,
    67 		    const_cast<int * >(indices),
    68 		    const_cast<Value * >(values));
    69   }
    70   
    71   void LpGlpk::_setColLowerBound(int i, Value lo)
    72   {
    73     if (lo==INF) {
    74       //FIXME error
    75     }
    76     int b=lpx_get_col_type(lp, i);
    77     double up=lpx_get_col_ub(lp, i);	
    78     if (lo==-INF) {
    79       switch (b) {
    80       case LPX_FR:
    81       case LPX_LO:
    82 	lpx_set_col_bnds(lp, i, LPX_FR, lo, up);
    83 	break;
    84       case LPX_UP:
    85 	break;
    86       case LPX_DB:
    87       case LPX_FX:
    88 	lpx_set_col_bnds(lp, i, LPX_UP, lo, up);
    89 	break;
    90       default: ;
    91 	//FIXME error
    92       }
    93     } else {
    94       switch (b) {
    95       case LPX_FR:
    96       case LPX_LO:
    97 	lpx_set_col_bnds(lp, i, LPX_LO, lo, up);
    98 	break;
    99       case LPX_UP:	  
   100       case LPX_DB:
   101       case LPX_FX:
   102 	if (lo==up) 
   103 	  lpx_set_col_bnds(lp, i, LPX_FX, lo, up);
   104 	else 
   105 	  lpx_set_col_bnds(lp, i, LPX_DB, lo, up);
   106 	break;
   107       default: ;
   108 	//FIXME error
   109       }
   110     }
   111 
   112   }
   113   
   114   void LpGlpk::_setColUpperBound(int i, Value up)
   115   {
   116     if (up==-INF) {
   117       //FIXME error
   118     }
   119     int b=lpx_get_col_type(lp, i);
   120     double lo=lpx_get_col_lb(lp, i);
   121     if (up==INF) {
   122       switch (b) {
   123       case LPX_FR:
   124       case LPX_LO:
   125 	break;
   126       case LPX_UP:
   127 	lpx_set_col_bnds(lp, i, LPX_FR, lo, up);
   128 	break;
   129       case LPX_DB:
   130       case LPX_FX:
   131 	lpx_set_col_bnds(lp, i, LPX_LO, lo, up);
   132 	break;
   133       default: ;
   134 	//FIXME error
   135       }
   136     } else {
   137       switch (b) {
   138       case LPX_FR:
   139 	lpx_set_col_bnds(lp, i, LPX_UP, lo, up);
   140 	break;
   141       case LPX_UP:
   142 	lpx_set_col_bnds(lp, i, LPX_UP, lo, up);
   143 	break;
   144       case LPX_LO:
   145       case LPX_DB:
   146       case LPX_FX:
   147 	if (lo==up) 
   148 	  lpx_set_col_bnds(lp, i, LPX_FX, lo, up);
   149 	else 
   150 	  lpx_set_col_bnds(lp, i, LPX_DB, lo, up);
   151 	break;
   152       default: ;
   153 	//FIXME error
   154       }
   155     }
   156   }
   157   
   158   void LpGlpk::_setRowLowerBound(int i, Value lo)
   159   {
   160     if (lo==INF) {
   161       //FIXME error
   162     }
   163     int b=lpx_get_row_type(lp, i);
   164     double up=lpx_get_row_ub(lp, i);	
   165     if (lo==-INF) {
   166       switch (b) {
   167       case LPX_FR:
   168       case LPX_LO:
   169 	lpx_set_row_bnds(lp, i, LPX_FR, lo, up);
   170 	break;
   171       case LPX_UP:
   172 	break;
   173       case LPX_DB:
   174       case LPX_FX:
   175 	lpx_set_row_bnds(lp, i, LPX_UP, lo, up);
   176 	break;
   177       default: ;
   178 	//FIXME error
   179       }
   180     } else {
   181       switch (b) {
   182       case LPX_FR:
   183       case LPX_LO:
   184 	lpx_set_row_bnds(lp, i, LPX_LO, lo, up);
   185 	break;
   186       case LPX_UP:	  
   187       case LPX_DB:
   188       case LPX_FX:
   189 	if (lo==up) 
   190 	  lpx_set_row_bnds(lp, i, LPX_FX, lo, up);
   191 	else 
   192 	  lpx_set_row_bnds(lp, i, LPX_DB, lo, up);
   193 	break;
   194       default: ;
   195 	//FIXME error
   196       }
   197     }
   198   }
   199   
   200   void LpGlpk::_setRowUpperBound(int i, Value up)
   201   {
   202     if (up==-INF) {
   203       //FIXME error
   204     }
   205     int b=lpx_get_row_type(lp, i);
   206     double lo=lpx_get_row_lb(lp, i);
   207     if (up==INF) {
   208       switch (b) {
   209       case LPX_FR:
   210       case LPX_LO:
   211 	break;
   212       case LPX_UP:
   213 	lpx_set_row_bnds(lp, i, LPX_FR, lo, up);
   214 	break;
   215       case LPX_DB:
   216       case LPX_FX:
   217 	lpx_set_row_bnds(lp, i, LPX_LO, lo, up);
   218 	break;
   219       default: ;
   220 	//FIXME error
   221       }
   222     } else {
   223       switch (b) {
   224       case LPX_FR:
   225 	lpx_set_row_bnds(lp, i, LPX_UP, lo, up);
   226 	break;
   227       case LPX_UP:
   228 	lpx_set_row_bnds(lp, i, LPX_UP, lo, up);
   229 	break;
   230       case LPX_LO:
   231       case LPX_DB:
   232       case LPX_FX:
   233 	if (lo==up) 
   234 	  lpx_set_row_bnds(lp, i, LPX_FX, lo, up);
   235 	else 
   236 	  lpx_set_row_bnds(lp, i, LPX_DB, lo, up);
   237 	break;
   238       default: ;
   239 	//FIXME error
   240       }
   241     }
   242   }
   243   
   244   void LpGlpk::_setObjCoeff(int i, Value obj_coef)
   245   {
   246     lpx_set_obj_coef(lp, i, obj_coef);
   247   }
   248 
   249 
   250   LpGlpk::SolveExitStatus LpGlpk::_solve()
   251   {
   252     int i=  lpx_simplex(lp);
   253     switch (i) {
   254     case LPX_E_OK: 
   255       return SOLVED;
   256       break;
   257     default:
   258       return UNSOLVED;
   259     }
   260   }
   261 
   262   LpGlpk::Value LpGlpk::_getPrimal(int i)
   263   {
   264     return lpx_get_col_prim(lp,i);
   265   }
   266   
   267   LpGlpk::Value LpGlpk::_getPrimalValue()
   268   {
   269     return lpx_get_obj_val(lp);
   270   }
   271   
   272  
   273   LpGlpk::SolutionStatus LpGlpk::_getPrimalStatus()
   274   {
   275     int stat=  lpx_get_status(lp);
   276     switch (stat) {
   277     case LPX_UNDEF://Undefined (no solve has been run yet)
   278       return UNDEFINED;
   279       break;
   280     case LPX_NOFEAS://There is no feasible solution (primal, I guess)
   281     case LPX_INFEAS://Infeasible 
   282       return INFEASIBLE;
   283       break;
   284     case LPX_UNBND://Unbounded
   285       return INFINITE;
   286       break;
   287     case LPX_FEAS://Feasible
   288       return FEASIBLE;
   289       break;
   290     case LPX_OPT://Feasible
   291       return OPTIMAL;
   292       break;
   293     default:
   294       return UNDEFINED; //to avoid gcc warning
   295       //FIXME error
   296     }
   297   }
   298 
   299 
   300   void LpGlpk::_setMax()
   301   {
   302     lpx_set_obj_dir(lp, LPX_MAX);
   303   }
   304 
   305   void LpGlpk::_setMin()
   306   {
   307     lpx_set_obj_dir(lp, LPX_MIN);
   308   }
   309 
   310  
   311   void LpGlpk::messageLevel(int m)
   312   {
   313     lpx_set_int_parm(lp, LPX_K_MSGLEV, m);
   314   }
   315 
   316   void LpGlpk::presolver(bool b)
   317   {
   318     lpx_set_int_parm(lp, LPX_K_PRESOL, b);
   319   }
   320 
   321  
   322 } //END OF NAMESPACE LEMON
   323 
   324 #endif //LEMON_LP_GLPK_CC