diff -r c9c2e90b2342 -r c3dc75d4af24 src/lemon/lp_glpk.cc --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/lemon/lp_glpk.cc Tue Apr 05 09:08:23 2005 +0000 @@ -0,0 +1,288 @@ +/* -*- C++ -*- + * src/lemon/lp_glpk.cc - Part of LEMON, a generic C++ optimization library + * + * Copyright (C) 2005 Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport + * (Egervary Combinatorial Optimization Research Group, EGRES). + * + * Permission to use, modify and distribute this software is granted + * provided that this copyright notice appears in all copies. For + * precise terms see the accompanying LICENSE file. + * + * This software is provided "AS IS" with no warranty of any kind, + * express or implied, and with no claim as to its suitability for any + * purpose. + * + */ + +#ifndef LEMON_LP_GLPK_CC +#define LEMON_LP_GLPK_CC + +///\file +///\brief Implementation of the LEMON-GLPK lp solver interface. + +#include + +namespace lemon { + + /// \e + int LpGlpk::_addCol() { + int i=lpx_add_cols(lp, 1); + _setColLowerBound(i, -INF); + _setColUpperBound(i, INF); + return i; + } + + /// \e + int LpGlpk::_addRow() { + int i=lpx_add_rows(lp, 1); + return i; + } + + + void LpGlpk::_setRowCoeffs(int i, + int length, + const int * indices, + const Value * values ) + { + lpx_set_mat_row(lp, i, length, + const_cast(indices) , + const_cast(values)); + } + + void LpGlpk::_setColCoeffs(int i, + int length, + const int * indices, + const Value * values) + { + lpx_set_mat_col(lp, i, length, + const_cast(indices), + const_cast(values)); + } + + void LpGlpk::_setColLowerBound(int i, Value lo) + { + if (lo==INF) { + //FIXME error + } + int b=lpx_get_col_type(lp, i); + double up=lpx_get_col_ub(lp, i); + if (lo==-INF) { + switch (b) { + case LPX_FR: + case LPX_LO: + lpx_set_col_bnds(lp, i, LPX_FR, lo, up); + break; + case LPX_UP: + break; + case LPX_DB: + case LPX_FX: + lpx_set_col_bnds(lp, i, LPX_UP, lo, up); + break; + default: ; + //FIXME error + } + } else { + switch (b) { + case LPX_FR: + case LPX_LO: + lpx_set_col_bnds(lp, i, LPX_LO, lo, up); + break; + case LPX_UP: + case LPX_DB: + case LPX_FX: + if (lo==up) + lpx_set_col_bnds(lp, i, LPX_FX, lo, up); + else + lpx_set_col_bnds(lp, i, LPX_DB, lo, up); + break; + default: ; + //FIXME error + } + } + + } + + void LpGlpk::_setColUpperBound(int i, Value up) + { + if (up==-INF) { + //FIXME error + } + int b=lpx_get_col_type(lp, i); + double lo=lpx_get_col_lb(lp, i); + if (up==INF) { + switch (b) { + case LPX_FR: + case LPX_LO: + break; + case LPX_UP: + lpx_set_col_bnds(lp, i, LPX_FR, lo, up); + break; + case LPX_DB: + case LPX_FX: + lpx_set_col_bnds(lp, i, LPX_LO, lo, up); + break; + default: ; + //FIXME error + } + } else { + switch (b) { + case LPX_FR: + lpx_set_col_bnds(lp, i, LPX_UP, lo, up); + break; + case LPX_UP: + lpx_set_col_bnds(lp, i, LPX_UP, lo, up); + break; + case LPX_LO: + case LPX_DB: + case LPX_FX: + if (lo==up) + lpx_set_col_bnds(lp, i, LPX_FX, lo, up); + else + lpx_set_col_bnds(lp, i, LPX_DB, lo, up); + break; + default: ; + //FIXME error + } + } + } + + void LpGlpk::_setRowLowerBound(int i, Value lo) + { + if (lo==INF) { + //FIXME error + } + int b=lpx_get_row_type(lp, i); + double up=lpx_get_row_ub(lp, i); + if (lo==-INF) { + switch (b) { + case LPX_FR: + case LPX_LO: + lpx_set_row_bnds(lp, i, LPX_FR, lo, up); + break; + case LPX_UP: + break; + case LPX_DB: + case LPX_FX: + lpx_set_row_bnds(lp, i, LPX_UP, lo, up); + break; + default: ; + //FIXME error + } + } else { + switch (b) { + case LPX_FR: + case LPX_LO: + lpx_set_row_bnds(lp, i, LPX_LO, lo, up); + break; + case LPX_UP: + case LPX_DB: + case LPX_FX: + if (lo==up) + lpx_set_row_bnds(lp, i, LPX_FX, lo, up); + else + lpx_set_row_bnds(lp, i, LPX_DB, lo, up); + break; + default: ; + //FIXME error + } + } + } + + void LpGlpk::_setRowUpperBound(int i, Value up) + { + if (up==-INF) { + //FIXME error + } + int b=lpx_get_row_type(lp, i); + double lo=lpx_get_row_lb(lp, i); + if (up==INF) { + switch (b) { + case LPX_FR: + case LPX_LO: + break; + case LPX_UP: + lpx_set_row_bnds(lp, i, LPX_FR, lo, up); + break; + case LPX_DB: + case LPX_FX: + lpx_set_row_bnds(lp, i, LPX_LO, lo, up); + break; + default: ; + //FIXME error + } + } else { + switch (b) { + case LPX_FR: + lpx_set_row_bnds(lp, i, LPX_UP, lo, up); + break; + case LPX_UP: + lpx_set_row_bnds(lp, i, LPX_UP, lo, up); + break; + case LPX_LO: + case LPX_DB: + case LPX_FX: + if (lo==up) + lpx_set_row_bnds(lp, i, LPX_FX, lo, up); + else + lpx_set_row_bnds(lp, i, LPX_DB, lo, up); + break; + default: ; + //FIXME error + } + } + } + + void LpGlpk::_setObjCoeff(int i, Value obj_coef) + { + lpx_set_obj_coef(lp, i, obj_coef); + } + + + LpGlpk::SolveExitStatus LpGlpk::_solve() + { + int i= lpx_simplex(lp); + switch (i) { + case LPX_E_OK: + return SOLVED; + break; + default: + return UNSOLVED; + } + } + + LpGlpk::Value LpGlpk::_getPrimal(int i) + { + return lpx_get_col_prim(lp,i); + } + + + LpGlpk::SolutionStatus LpGlpk::_getPrimalType() + { + int stat= lpx_get_status(lp); + switch (stat) { + case LPX_UNDEF://Undefined (no solve has been run yet) + return UNDEFINED; + break; + case LPX_NOFEAS://There is no feasible solution (primal, I guess) + case LPX_INFEAS://Infeasible + return INFEASIBLE; + break; + case LPX_UNBND://Unbounded + return INFINITE; + break; + case LPX_FEAS://Feasible + return FEASIBLE; + break; + case LPX_OPT://Feasible + return OPTIMAL; + break; + default: + return UNDEFINED; //to avoid gcc warning + //FIXME error + } + } + + +} //END OF NAMESPACE LEMON + +#endif //LEMON_LP_GLPK_CC