1.1 --- a/lemon/lp_glpk.cc Mon May 07 11:42:18 2007 +0000
1.2 +++ b/lemon/lp_glpk.cc Mon May 07 18:19:55 2007 +0000
1.3 @@ -21,61 +21,84 @@
1.4
1.5 #include <lemon/lp_glpk.h>
1.6 //#include <iostream>
1.7 +
1.8 +#if GLP_MAJOR_VERSION > 4 || (GLP_MAJOR_VERSION == 4 && GLP_MINOR_VERSION > 15)
1.9 +#define LEMON_glp(func) (glp_##func)
1.10 +#define LEMON_lpx(func) (lpx_##func)
1.11 +
1.12 +#define LEMON_GLP(def) (GLP_##def)
1.13 +#define LEMON_LPX(def) (LPX_##def)
1.14 +
1.15 +#else
1.16 +
1.17 +#define LEMON_glp(func) (lpx_##func)
1.18 +#define LEMON_lpx(func) (lpx_##func)
1.19 +
1.20 +#define LEMON_GLP(def) (LPX_##def)
1.21 +#define LEMON_LPX(def) (LPX_##def)
1.22 +
1.23 +#endif
1.24 +
1.25 namespace lemon {
1.26
1.27 -
1.28 LpGlpk::LpGlpk() : Parent() {
1.29 + solved = false;
1.30 rows = _lp_bits::LpId(1);
1.31 cols = _lp_bits::LpId(1);
1.32 - lp = lpx_create_prob();
1.33 - lpx_create_index(lp);
1.34 - ///\todo control function for this:
1.35 - lpx_set_int_parm(lp, LPX_K_DUAL, 1);
1.36 + lp = LEMON_glp(create_prob)();
1.37 + LEMON_glp(create_index)(lp);
1.38 + LEMON_lpx(set_int_parm)(lp, LEMON_LPX(K_DUAL), 1);
1.39 messageLevel(0);
1.40 }
1.41
1.42 LpGlpk::LpGlpk(const LpGlpk &glp) : Parent() {
1.43 + solved = false;
1.44 rows = _lp_bits::LpId(1);
1.45 cols = _lp_bits::LpId(1);
1.46 - lp = lpx_create_prob();
1.47 - lpx_create_index(lp);
1.48 + lp = LEMON_glp(create_prob)();
1.49 + LEMON_glp(create_index)(lp);
1.50 ///\todo control function for this:
1.51 - lpx_set_int_parm(lp, LPX_K_DUAL, 1);
1.52 + LEMON_lpx(set_int_parm)(lp, LEMON_LPX(K_DUAL), 1);
1.53 messageLevel(0);
1.54 //Coefficient matrix, row bounds
1.55 - lpx_add_rows(lp, lpx_get_num_rows(glp.lp));
1.56 - lpx_add_cols(lp, lpx_get_num_cols(glp.lp));
1.57 + LEMON_glp(add_rows)(lp, LEMON_glp(get_num_rows)(glp.lp));
1.58 + LEMON_glp(add_cols)(lp, LEMON_glp(get_num_cols)(glp.lp));
1.59 int len;
1.60 - int ind[1+lpx_get_num_cols(glp.lp)];
1.61 - Value val[1+lpx_get_num_cols(glp.lp)];
1.62 - for (int i=1;i<=lpx_get_num_rows(glp.lp);++i)
1.63 + int ind[1+LEMON_glp(get_num_cols)(glp.lp)];
1.64 + Value val[1+LEMON_glp(get_num_cols)(glp.lp)];
1.65 + for (int i=1;i<=LEMON_glp(get_num_rows)(glp.lp);++i)
1.66 {
1.67 - len=lpx_get_mat_row(glp.lp,i,ind,val);
1.68 - lpx_set_mat_row(lp, i,len,ind,val);
1.69 - lpx_set_row_bnds(lp,i,lpx_get_row_type(glp.lp,i),
1.70 - lpx_get_row_lb(glp.lp,i),lpx_get_row_ub(glp.lp,i));
1.71 + len=LEMON_glp(get_mat_row)(glp.lp,i,ind,val);
1.72 + LEMON_glp(set_mat_row)(lp, i,len,ind,val);
1.73 + LEMON_glp(set_row_bnds)(lp,i,
1.74 + LEMON_glp(get_row_type)(glp.lp,i),
1.75 + LEMON_glp(get_row_lb)(glp.lp,i),
1.76 + LEMON_glp(get_row_ub)(glp.lp,i));
1.77 }
1.78
1.79 //Objective function, coloumn bounds
1.80 - lpx_set_obj_dir(lp, lpx_get_obj_dir(glp.lp));
1.81 + LEMON_glp(set_obj_dir)(lp, LEMON_glp(get_obj_dir)(glp.lp));
1.82 //Objectif function's constant term treated separately
1.83 - lpx_set_obj_coef(lp,0,lpx_get_obj_coef(glp.lp,0));
1.84 - for (int i=1;i<=lpx_get_num_cols(glp.lp);++i)
1.85 + LEMON_glp(set_obj_coef)(lp,0,LEMON_glp(get_obj_coef)(glp.lp,0));
1.86 + for (int i=1;i<=LEMON_glp(get_num_cols)(glp.lp);++i)
1.87 {
1.88 - lpx_set_obj_coef(lp,i,lpx_get_obj_coef(glp.lp,i));
1.89 - lpx_set_col_bnds(lp,i,lpx_get_col_type(glp.lp,i),
1.90 - lpx_get_col_lb(glp.lp,i),lpx_get_col_ub(glp.lp,i));
1.91 + LEMON_glp(set_obj_coef)(lp,i,
1.92 + LEMON_glp(get_obj_coef)(glp.lp,i));
1.93 + LEMON_glp(set_col_bnds)(lp,i,
1.94 + LEMON_glp(get_col_type)(glp.lp,i),
1.95 + LEMON_glp(get_col_lb)(glp.lp,i),
1.96 + LEMON_glp(get_col_ub)(glp.lp,i));
1.97 }
1.98 }
1.99
1.100 LpGlpk::~LpGlpk() {
1.101 - lpx_delete_prob(lp);
1.102 + LEMON_glp(delete_prob)(lp);
1.103 }
1.104
1.105 int LpGlpk::_addCol() {
1.106 - int i=lpx_add_cols(lp, 1);
1.107 - _setColLowerBound(i, -INF);
1.108 - _setColUpperBound(i, INF);
1.109 + int i=LEMON_glp(add_cols)(lp, 1);
1.110 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(FR), 0.0, 0.0);
1.111 + solved = false;
1.112 return i;
1.113 }
1.114
1.115 @@ -97,7 +120,8 @@
1.116 }
1.117
1.118 int LpGlpk::_addRow() {
1.119 - int i=lpx_add_rows(lp, 1);
1.120 + int i=LEMON_glp(add_rows)(lp, 1);
1.121 + solved = false;
1.122 return i;
1.123 }
1.124
1.125 @@ -105,32 +129,34 @@
1.126 void LpGlpk::_eraseCol(int i) {
1.127 int ca[2];
1.128 ca[1]=i;
1.129 - lpx_del_cols(lp, 1, ca);
1.130 + LEMON_glp(del_cols)(lp, 1, ca);
1.131 + solved = false;
1.132 }
1.133
1.134 void LpGlpk::_eraseRow(int i) {
1.135 int ra[2];
1.136 ra[1]=i;
1.137 - lpx_del_rows(lp, 1, ra);
1.138 + LEMON_glp(del_rows)(lp, 1, ra);
1.139 + solved = false;
1.140 }
1.141
1.142 void LpGlpk::_getColName(int c, std::string & name) const
1.143 {
1.144
1.145 - char *n = lpx_get_col_name(lp,c);
1.146 + const char *n = LEMON_glp(get_col_name)(lp,c);
1.147 name = n?n:"";
1.148 }
1.149
1.150
1.151 void LpGlpk::_setColName(int c, const std::string & name)
1.152 {
1.153 - lpx_set_col_name(lp,c,const_cast<char*>(name.c_str()));
1.154 + LEMON_glp(set_col_name)(lp,c,const_cast<char*>(name.c_str()));
1.155
1.156 }
1.157
1.158 int LpGlpk::_colByName(const std::string& name) const
1.159 {
1.160 - int k = lpx_find_col(lp, const_cast<char*>(name.c_str()));
1.161 + int k = LEMON_glp(find_col)(lp, const_cast<char*>(name.c_str()));
1.162 return k > 0 ? k : -1;
1.163 }
1.164
1.165 @@ -148,17 +174,20 @@
1.166 values.push_back(it->second);
1.167 }
1.168
1.169 - lpx_set_mat_row(lp, i, values.size() - 1, &indices[0], &values[0]);
1.170 + LEMON_glp(set_mat_row)(lp, i, values.size() - 1,
1.171 + &indices[0], &values[0]);
1.172 +
1.173 + solved = false;
1.174 }
1.175
1.176 void LpGlpk::_getRowCoeffs(int ix, RowIterator b) const
1.177 {
1.178 - int length = lpx_get_mat_row(lp, ix, 0, 0);
1.179 + int length = LEMON_glp(get_mat_row)(lp, ix, 0, 0);
1.180
1.181 std::vector<int> indices(length + 1);
1.182 std::vector<Value> values(length + 1);
1.183
1.184 - lpx_get_mat_row(lp, ix, &indices[0], &values[0]);
1.185 + LEMON_glp(get_mat_row)(lp, ix, &indices[0], &values[0]);
1.186
1.187 for (int i = 1; i <= length; ++i) {
1.188 *b = std::make_pair(indices[i], values[i]);
1.189 @@ -179,17 +208,20 @@
1.190 values.push_back(it->second);
1.191 }
1.192
1.193 - lpx_set_mat_col(lp, ix, values.size() - 1, &indices[0], &values[0]);
1.194 + LEMON_glp(set_mat_col)(lp, ix, values.size() - 1,
1.195 + &indices[0], &values[0]);
1.196 +
1.197 + solved = false;
1.198 }
1.199
1.200 void LpGlpk::_getColCoeffs(int ix, ColIterator b) const
1.201 {
1.202 - int length = lpx_get_mat_col(lp, ix, 0, 0);
1.203 + int length = LEMON_glp(get_mat_col)(lp, ix, 0, 0);
1.204
1.205 std::vector<int> indices(length + 1);
1.206 std::vector<Value> values(length + 1);
1.207
1.208 - lpx_get_mat_col(lp, ix, &indices[0], &values[0]);
1.209 + LEMON_glp(get_mat_col)(lp, ix, &indices[0], &values[0]);
1.210
1.211 for (int i = 1; i <= length; ++i) {
1.212 *b = std::make_pair(indices[i], values[i]);
1.213 @@ -200,14 +232,14 @@
1.214 void LpGlpk::_setCoeff(int ix, int jx, Value value)
1.215 {
1.216
1.217 - if (lpx_get_num_cols(lp) < lpx_get_num_rows(lp)) {
1.218 + if (LEMON_glp(get_num_cols)(lp) < LEMON_glp(get_num_rows)(lp)) {
1.219
1.220 - int length=lpx_get_mat_row(lp, ix, 0, 0);
1.221 + int length=LEMON_glp(get_mat_row)(lp, ix, 0, 0);
1.222
1.223 std::vector<int> indices(length + 2);
1.224 std::vector<Value> values(length + 2);
1.225
1.226 - lpx_get_mat_row(lp, ix, &indices[0], &values[0]);
1.227 + LEMON_glp(get_mat_row)(lp, ix, &indices[0], &values[0]);
1.228
1.229 //The following code does not suppose that the elements of the
1.230 //array indices are sorted
1.231 @@ -225,16 +257,16 @@
1.232 values[length]=value;
1.233 }
1.234
1.235 - lpx_set_mat_row(lp, ix, length, &indices[0], &values[0]);
1.236 + LEMON_glp(set_mat_row)(lp, ix, length, &indices[0], &values[0]);
1.237
1.238 } else {
1.239
1.240 - int length=lpx_get_mat_col(lp, jx, 0, 0);
1.241 + int length=LEMON_glp(get_mat_col)(lp, jx, 0, 0);
1.242
1.243 std::vector<int> indices(length + 2);
1.244 std::vector<Value> values(length + 2);
1.245
1.246 - lpx_get_mat_col(lp, jx, &indices[0], &values[0]);
1.247 + LEMON_glp(get_mat_col)(lp, jx, &indices[0], &values[0]);
1.248
1.249 //The following code does not suppose that the elements of the
1.250 //array indices are sorted
1.251 @@ -252,19 +284,21 @@
1.252 values[length]=value;
1.253 }
1.254
1.255 - lpx_set_mat_col(lp, jx, length, &indices[0], &values[0]);
1.256 + LEMON_glp(set_mat_col)(lp, jx, length, &indices[0], &values[0]);
1.257 }
1.258 +
1.259 + solved = false;
1.260 }
1.261
1.262 LpGlpk::Value LpGlpk::_getCoeff(int ix, int jx) const
1.263 {
1.264
1.265 - int length=lpx_get_mat_row(lp, ix, 0, 0);
1.266 + int length=LEMON_glp(get_mat_row)(lp, ix, 0, 0);
1.267
1.268 std::vector<int> indices(length + 1);
1.269 std::vector<Value> values(length + 1);
1.270
1.271 - lpx_get_mat_row(lp, ix, &indices[0], &values[0]);
1.272 + LEMON_glp(get_mat_row)(lp, ix, &indices[0], &values[0]);
1.273
1.274 //The following code does not suppose that the elements of the
1.275 //array indices are sorted
1.276 @@ -283,52 +317,53 @@
1.277 if (lo==INF) {
1.278 //FIXME error
1.279 }
1.280 - int b=lpx_get_col_type(lp, i);
1.281 - double up=lpx_get_col_ub(lp, i);
1.282 + int b=LEMON_glp(get_col_type)(lp, i);
1.283 + double up=LEMON_glp(get_col_ub)(lp, i);
1.284 if (lo==-INF) {
1.285 switch (b) {
1.286 - case LPX_FR:
1.287 - case LPX_LO:
1.288 - lpx_set_col_bnds(lp, i, LPX_FR, lo, up);
1.289 + case LEMON_GLP(FR):
1.290 + case LEMON_GLP(LO):
1.291 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(FR), lo, up);
1.292 break;
1.293 - case LPX_UP:
1.294 + case LEMON_GLP(UP):
1.295 break;
1.296 - case LPX_DB:
1.297 - case LPX_FX:
1.298 - lpx_set_col_bnds(lp, i, LPX_UP, lo, up);
1.299 + case LEMON_GLP(DB):
1.300 + case LEMON_GLP(FX):
1.301 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(UP), lo, up);
1.302 break;
1.303 default: ;
1.304 //FIXME error
1.305 }
1.306 } else {
1.307 switch (b) {
1.308 - case LPX_FR:
1.309 - case LPX_LO:
1.310 - lpx_set_col_bnds(lp, i, LPX_LO, lo, up);
1.311 + case LEMON_GLP(FR):
1.312 + case LEMON_GLP(LO):
1.313 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(LO), lo, up);
1.314 break;
1.315 - case LPX_UP:
1.316 - case LPX_DB:
1.317 - case LPX_FX:
1.318 + case LEMON_GLP(UP):
1.319 + case LEMON_GLP(DB):
1.320 + case LEMON_GLP(FX):
1.321 if (lo==up)
1.322 - lpx_set_col_bnds(lp, i, LPX_FX, lo, up);
1.323 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(FX), lo, up);
1.324 else
1.325 - lpx_set_col_bnds(lp, i, LPX_DB, lo, up);
1.326 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(DB), lo, up);
1.327 break;
1.328 default: ;
1.329 //FIXME error
1.330 }
1.331 }
1.332
1.333 + solved = false;
1.334 }
1.335
1.336 LpGlpk::Value LpGlpk::_getColLowerBound(int i) const
1.337 {
1.338 - int b=lpx_get_col_type(lp, i);
1.339 + int b=LEMON_glp(get_col_type)(lp, i);
1.340 switch (b) {
1.341 - case LPX_LO:
1.342 - case LPX_DB:
1.343 - case LPX_FX:
1.344 - return lpx_get_col_lb(lp, i);
1.345 + case LEMON_GLP(LO):
1.346 + case LEMON_GLP(DB):
1.347 + case LEMON_GLP(FX):
1.348 + return LEMON_glp(get_col_lb)(lp, i);
1.349 default: ;
1.350 return -INF;
1.351 }
1.352 @@ -339,53 +374,55 @@
1.353 if (up==-INF) {
1.354 //FIXME error
1.355 }
1.356 - int b=lpx_get_col_type(lp, i);
1.357 - double lo=lpx_get_col_lb(lp, i);
1.358 + int b=LEMON_glp(get_col_type)(lp, i);
1.359 + double lo=LEMON_glp(get_col_lb)(lp, i);
1.360 if (up==INF) {
1.361 switch (b) {
1.362 - case LPX_FR:
1.363 - case LPX_LO:
1.364 + case LEMON_GLP(FR):
1.365 + case LEMON_GLP(LO):
1.366 break;
1.367 - case LPX_UP:
1.368 - lpx_set_col_bnds(lp, i, LPX_FR, lo, up);
1.369 + case LEMON_GLP(UP):
1.370 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(FR), lo, up);
1.371 break;
1.372 - case LPX_DB:
1.373 - case LPX_FX:
1.374 - lpx_set_col_bnds(lp, i, LPX_LO, lo, up);
1.375 + case LEMON_GLP(DB):
1.376 + case LEMON_GLP(FX):
1.377 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(LO), lo, up);
1.378 break;
1.379 default: ;
1.380 //FIXME error
1.381 }
1.382 } else {
1.383 switch (b) {
1.384 - case LPX_FR:
1.385 - lpx_set_col_bnds(lp, i, LPX_UP, lo, up);
1.386 + case LEMON_GLP(FR):
1.387 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(UP), lo, up);
1.388 break;
1.389 - case LPX_UP:
1.390 - lpx_set_col_bnds(lp, i, LPX_UP, lo, up);
1.391 + case LEMON_GLP(UP):
1.392 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(UP), lo, up);
1.393 break;
1.394 - case LPX_LO:
1.395 - case LPX_DB:
1.396 - case LPX_FX:
1.397 + case LEMON_GLP(LO):
1.398 + case LEMON_GLP(DB):
1.399 + case LEMON_GLP(FX):
1.400 if (lo==up)
1.401 - lpx_set_col_bnds(lp, i, LPX_FX, lo, up);
1.402 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(FX), lo, up);
1.403 else
1.404 - lpx_set_col_bnds(lp, i, LPX_DB, lo, up);
1.405 + LEMON_glp(set_col_bnds)(lp, i, LEMON_GLP(DB), lo, up);
1.406 break;
1.407 default: ;
1.408 //FIXME error
1.409 }
1.410 }
1.411 +
1.412 + solved = false;
1.413 }
1.414
1.415 LpGlpk::Value LpGlpk::_getColUpperBound(int i) const
1.416 {
1.417 - int b=lpx_get_col_type(lp, i);
1.418 + int b=LEMON_glp(get_col_type)(lp, i);
1.419 switch (b) {
1.420 - case LPX_UP:
1.421 - case LPX_DB:
1.422 - case LPX_FX:
1.423 - return lpx_get_col_ub(lp, i);
1.424 + case LEMON_GLP(UP):
1.425 + case LEMON_GLP(DB):
1.426 + case LEMON_GLP(FX):
1.427 + return LEMON_glp(get_col_ub)(lp, i);
1.428 default: ;
1.429 return INF;
1.430 }
1.431 @@ -400,49 +437,50 @@
1.432
1.433 if (lb == -INF){
1.434 if (ub == INF){
1.435 - lpx_set_row_bnds(lp, i, LPX_FR, lb, ub);
1.436 + LEMON_glp(set_row_bnds)(lp, i, LEMON_GLP(FR), lb, ub);
1.437 }
1.438 else{
1.439 - lpx_set_row_bnds(lp, i, LPX_UP, lb, ub);
1.440 + LEMON_glp(set_row_bnds)(lp, i, LEMON_GLP(UP), lb, ub);
1.441 }
1.442 }
1.443 else{
1.444 if (ub==INF){
1.445 - lpx_set_row_bnds(lp, i, LPX_LO, lb, ub);
1.446 + LEMON_glp(set_row_bnds)(lp, i, LEMON_GLP(LO), lb, ub);
1.447
1.448 }
1.449 else{
1.450 if (lb == ub){
1.451 - lpx_set_row_bnds(lp, i, LPX_FX, lb, ub);
1.452 + LEMON_glp(set_row_bnds)(lp, i, LEMON_GLP(FX), lb, ub);
1.453 }
1.454 else{
1.455 - lpx_set_row_bnds(lp, i, LPX_DB, lb, ub);
1.456 + LEMON_glp(set_row_bnds)(lp, i, LEMON_GLP(DB), lb, ub);
1.457 }
1.458 }
1.459 }
1.460
1.461 + solved = false;
1.462 }
1.463
1.464 void LpGlpk::_getRowBounds(int i, Value &lb, Value &ub) const
1.465 {
1.466
1.467 - int b=lpx_get_row_type(lp, i);
1.468 + int b=LEMON_glp(get_row_type)(lp, i);
1.469 switch (b) {
1.470 - case LPX_FR:
1.471 - case LPX_UP:
1.472 + case LEMON_GLP(FR):
1.473 + case LEMON_GLP(UP):
1.474 lb = -INF;
1.475 break;
1.476 default:
1.477 - lb=lpx_get_row_lb(lp, i);
1.478 + lb=LEMON_glp(get_row_lb)(lp, i);
1.479 }
1.480
1.481 switch (b) {
1.482 - case LPX_FR:
1.483 - case LPX_LO:
1.484 + case LEMON_GLP(FR):
1.485 + case LEMON_GLP(LO):
1.486 ub = INF;
1.487 break;
1.488 default:
1.489 - ub=lpx_get_row_ub(lp, i);
1.490 + ub=LEMON_glp(get_row_ub)(lp, i);
1.491 }
1.492
1.493 }
1.494 @@ -450,31 +488,36 @@
1.495 void LpGlpk::_setObjCoeff(int i, Value obj_coef)
1.496 {
1.497 //i=0 means the constant term (shift)
1.498 - lpx_set_obj_coef(lp, i, obj_coef);
1.499 + LEMON_glp(set_obj_coef)(lp, i, obj_coef);
1.500 +
1.501 + solved = false;
1.502 }
1.503
1.504 LpGlpk::Value LpGlpk::_getObjCoeff(int i) const {
1.505 //i=0 means the constant term (shift)
1.506 - return lpx_get_obj_coef(lp, i);
1.507 + return LEMON_glp(get_obj_coef)(lp, i);
1.508 }
1.509
1.510 void LpGlpk::_clearObj()
1.511 {
1.512 - for (int i=0;i<=lpx_get_num_cols(lp);++i){
1.513 - lpx_set_obj_coef(lp, i, 0);
1.514 + for (int i=0;i<=LEMON_glp(get_num_cols)(lp);++i){
1.515 + LEMON_glp(set_obj_coef)(lp, i, 0);
1.516 }
1.517 +
1.518 + solved = false;
1.519 }
1.520
1.521 LpGlpk::SolveExitStatus LpGlpk::_solve()
1.522 {
1.523 // A way to check the problem to be solved
1.524 - //lpx_write_cpxlp(lp,"naittvan.cpx");
1.525 + //LEMON_glp(write_cpxlp(lp,"naittvan.cpx");
1.526
1.527 - lpx_std_basis(lp);
1.528 - int i = lpx_simplex(lp);
1.529 + LEMON_lpx(std_basis)(lp);
1.530 + int i = LEMON_lpx(simplex)(lp);
1.531
1.532 switch (i) {
1.533 - case LPX_E_OK:
1.534 + case LEMON_LPX(E_OK):
1.535 + solved = true;
1.536 return SOLVED;
1.537 default:
1.538 return UNSOLVED;
1.539 @@ -483,38 +526,39 @@
1.540
1.541 LpGlpk::Value LpGlpk::_getPrimal(int i) const
1.542 {
1.543 - return lpx_get_col_prim(lp,i);
1.544 + return LEMON_glp(get_col_prim)(lp,i);
1.545 }
1.546
1.547 LpGlpk::Value LpGlpk::_getDual(int i) const
1.548 {
1.549 - return lpx_get_row_dual(lp,i);
1.550 + return LEMON_glp(get_row_dual)(lp,i);
1.551 }
1.552
1.553 LpGlpk::Value LpGlpk::_getPrimalValue() const
1.554 {
1.555 - return lpx_get_obj_val(lp);
1.556 + return LEMON_glp(get_obj_val)(lp);
1.557 }
1.558 bool LpGlpk::_isBasicCol(int i) const
1.559 {
1.560 - return (lpx_get_col_stat(lp, i)==LPX_BS);
1.561 + return (LEMON_glp(get_col_stat)(lp, i)==LEMON_GLP(BS));
1.562 }
1.563
1.564
1.565 LpGlpk::SolutionStatus LpGlpk::_getPrimalStatus() const
1.566 {
1.567 - int stat= lpx_get_status(lp);
1.568 + if (!solved) return UNDEFINED;
1.569 + int stat= LEMON_lpx(get_status)(lp);
1.570 switch (stat) {
1.571 - case LPX_UNDEF://Undefined (no solve has been run yet)
1.572 + case LEMON_LPX(UNDEF)://Undefined (no solve has been run yet)
1.573 return UNDEFINED;
1.574 - case LPX_NOFEAS://There is no feasible solution (primal, I guess)
1.575 - case LPX_INFEAS://Infeasible
1.576 + case LEMON_LPX(NOFEAS)://There is no feasible solution (primal, I guess)
1.577 + case LEMON_LPX(INFEAS)://Infeasible
1.578 return INFEASIBLE;
1.579 - case LPX_UNBND://Unbounded
1.580 + case LEMON_LPX(UNBND)://Unbounded
1.581 return INFINITE;
1.582 - case LPX_FEAS://Feasible
1.583 + case LEMON_LPX(FEAS)://Feasible
1.584 return FEASIBLE;
1.585 - case LPX_OPT://Feasible
1.586 + case LEMON_LPX(OPT)://Feasible
1.587 return OPTIMAL;
1.588 default:
1.589 return UNDEFINED; //to avoid gcc warning
1.590 @@ -524,17 +568,18 @@
1.591
1.592 LpGlpk::SolutionStatus LpGlpk::_getDualStatus() const
1.593 {
1.594 - switch (lpx_get_dual_stat(lp)) {
1.595 - case LPX_D_UNDEF://Undefined (no solve has been run yet)
1.596 + if (!solved) return UNDEFINED;
1.597 + switch (LEMON_lpx(get_dual_stat)(lp)) {
1.598 + case LEMON_LPX(D_UNDEF)://Undefined (no solve has been run yet)
1.599 return UNDEFINED;
1.600 - case LPX_D_NOFEAS://There is no dual feasible solution
1.601 -// case LPX_D_INFEAS://Infeasible
1.602 + case LEMON_LPX(D_NOFEAS)://There is no dual feasible solution
1.603 +// case LEMON_LPX(D_INFEAS://Infeasible
1.604 return INFEASIBLE;
1.605 - case LPX_D_FEAS://Feasible
1.606 - switch (lpx_get_status(lp)) {
1.607 - case LPX_NOFEAS:
1.608 + case LEMON_LPX(D_FEAS)://Feasible
1.609 + switch (LEMON_lpx(get_status)(lp)) {
1.610 + case LEMON_LPX(NOFEAS):
1.611 return INFINITE;
1.612 - case LPX_OPT:
1.613 + case LEMON_LPX(OPT):
1.614 return OPTIMAL;
1.615 default:
1.616 return FEASIBLE;
1.617 @@ -547,16 +592,17 @@
1.618
1.619 LpGlpk::ProblemTypes LpGlpk::_getProblemType() const
1.620 {
1.621 - //int stat= lpx_get_status(lp);
1.622 - int statp= lpx_get_prim_stat(lp);
1.623 - int statd= lpx_get_dual_stat(lp);
1.624 - if (statp==LPX_P_FEAS && statd==LPX_D_FEAS)
1.625 + if (!solved) return UNKNOWN;
1.626 + //int stat= LEMON_glp(get_status(lp);
1.627 + int statp= LEMON_lpx(get_prim_stat)(lp);
1.628 + int statd= LEMON_lpx(get_dual_stat)(lp);
1.629 + if (statp==LEMON_LPX(P_FEAS) && statd==LEMON_LPX(D_FEAS))
1.630 return PRIMAL_DUAL_FEASIBLE;
1.631 - if (statp==LPX_P_FEAS && statd==LPX_D_NOFEAS)
1.632 + if (statp==LEMON_LPX(P_FEAS) && statd==LEMON_LPX(D_NOFEAS))
1.633 return PRIMAL_FEASIBLE_DUAL_INFEASIBLE;
1.634 - if (statp==LPX_P_NOFEAS && statd==LPX_D_FEAS)
1.635 + if (statp==LEMON_LPX(P_NOFEAS) && statd==LEMON_LPX(D_FEAS))
1.636 return PRIMAL_INFEASIBLE_DUAL_FEASIBLE;
1.637 - if (statp==LPX_P_NOFEAS && statd==LPX_D_NOFEAS)
1.638 + if (statp==LEMON_LPX(P_NOFEAS) && statd==LEMON_LPX(D_NOFEAS))
1.639 return PRIMAL_DUAL_INFEASIBLE;
1.640 //In all other cases
1.641 return UNKNOWN;
1.642 @@ -564,29 +610,31 @@
1.643
1.644 void LpGlpk::_setMax()
1.645 {
1.646 - lpx_set_obj_dir(lp, LPX_MAX);
1.647 + solved = false;
1.648 + LEMON_glp(set_obj_dir)(lp, LEMON_GLP(MAX));
1.649 }
1.650
1.651 void LpGlpk::_setMin()
1.652 {
1.653 - lpx_set_obj_dir(lp, LPX_MIN);
1.654 + solved = false;
1.655 + LEMON_glp(set_obj_dir)(lp, LEMON_GLP(MIN));
1.656 }
1.657
1.658 bool LpGlpk::_isMax() const
1.659 {
1.660 - return (lpx_get_obj_dir(lp)==LPX_MAX);
1.661 + return (LEMON_glp(get_obj_dir)(lp)==LEMON_GLP(MAX));
1.662 }
1.663
1.664
1.665
1.666 void LpGlpk::messageLevel(int m)
1.667 {
1.668 - lpx_set_int_parm(lp, LPX_K_MSGLEV, m);
1.669 + LEMON_lpx(set_int_parm)(lp, LEMON_LPX(K_MSGLEV), m);
1.670 }
1.671
1.672 void LpGlpk::presolver(bool b)
1.673 {
1.674 - lpx_set_int_parm(lp, LPX_K_PRESOL, b);
1.675 + LEMON_lpx(set_int_parm)(lp, LEMON_LPX(K_PRESOL), b);
1.676 }
1.677
1.678
2.1 --- a/lemon/lp_glpk.h Mon May 07 11:42:18 2007 +0000
2.2 +++ b/lemon/lp_glpk.h Mon May 07 18:19:55 2007 +0000
2.3 @@ -38,6 +38,7 @@
2.4 class LpGlpk : virtual public LpSolverBase {
2.5 protected:
2.6 LPX* lp;
2.7 + bool solved;
2.8
2.9 public:
2.10
3.1 --- a/lemon/mip_glpk.cc Mon May 07 11:42:18 2007 +0000
3.2 +++ b/lemon/mip_glpk.cc Mon May 07 18:19:55 2007 +0000
3.3 @@ -21,19 +21,38 @@
3.4
3.5 #include <lemon/mip_glpk.h>
3.6
3.7 +#if GLP_MAJOR_VERSION > 4 || (GLP_MAJOR_VERSION == 4 && GLP_MINOR_VERSION > 15)
3.8 +#define LEMON_glp(func) (glp_##func)
3.9 +#define LEMON_lpx(func) (lpx_##func)
3.10 +
3.11 +#define LEMON_GLP(def) (GLP_##def)
3.12 +#define LEMON_LPX(def) (LPX_##def)
3.13 +
3.14 +#else
3.15 +
3.16 +#define LEMON_glp(func) (lpx_##func)
3.17 +#define LEMON_lpx(func) (lpx_##func)
3.18 +
3.19 +#define LEMON_GLP(def) (LPX_##def)
3.20 +#define LEMON_LPX(def) (LPX_##def)
3.21 +
3.22 +#endif
3.23 +
3.24 namespace lemon {
3.25
3.26 MipGlpk::MipGlpk() {
3.27 - lpx_set_class(lp,LPX_MIP);
3.28 +#if !(GLP_MAJOR_VERSION > 4 || (GLP_MAJOR_VERSION == 4 && GLP_MINOR_VERSION > 15))
3.29 + LEMON_lpx(set_class)(lp,LEMON_GLP(MIP));
3.30 +#endif
3.31 }
3.32
3.33 void MipGlpk::_colType(int i, MipGlpk::ColTypes col_type){
3.34 switch (col_type){
3.35 case INT:
3.36 - lpx_set_col_kind(lp,i,LPX_IV);
3.37 + LEMON_glp(set_col_kind)(lp,i,LEMON_GLP(IV));
3.38 break;
3.39 case REAL:
3.40 - lpx_set_col_kind(lp,i,LPX_CV);
3.41 + LEMON_glp(set_col_kind)(lp,i,LEMON_GLP(CV));
3.42 break;
3.43 default:;
3.44 //FIXME problem
3.45 @@ -41,10 +60,10 @@
3.46 }
3.47
3.48 MipGlpk::ColTypes MipGlpk::_colType(int i) const {
3.49 - switch (lpx_get_col_kind(lp,i)){
3.50 - case LPX_IV:
3.51 + switch (LEMON_glp(get_col_kind)(lp,i)){
3.52 + case LEMON_GLP(IV):
3.53 return INT;//Or binary
3.54 - case LPX_CV:
3.55 + case LEMON_GLP(CV):
3.56 return REAL;
3.57 default:
3.58 return REAL;//Error!
3.59 @@ -53,44 +72,63 @@
3.60 }
3.61
3.62 LpGlpk::SolveExitStatus MipGlpk::_solve() {
3.63 - int result = lpx_simplex(lp);
3.64 - //
3.65 - if (lpx_get_status(lp)==LPX_OPT){
3.66 + int result = LEMON_lpx(simplex)(lp);
3.67 +
3.68 + // hack: mip does not contain integer variable
3.69 +#if GLP_MAJOR_VERSION > 4 || (GLP_MAJOR_VERSION == 4 && GLP_MINOR_VERSION > 15)
3.70 + int tmp = -1;
3.71 + if (LEMON_glp(get_num_int(lp)) == 0) {
3.72 + tmp = LEMON_lpx(add_cols)(lp, 1);
3.73 + LEMON_glp(set_col_bnds)(lp, tmp, LEMON_GLP(FX), 0.0, 0.0);
3.74 + LEMON_glp(set_col_kind)(lp, tmp, LEMON_GLP(IV));
3.75 + }
3.76 +#endif
3.77 +
3.78 + if (LEMON_lpx(get_status)(lp)==LEMON_LPX(OPT)) {
3.79 //Maybe we could try the routine lpx_intopt(lp), a revised
3.80 //version of lpx_integer
3.81 - result = lpx_integer(lp);
3.82 +
3.83 + result = LEMON_lpx(integer)(lp);
3.84 switch (result){
3.85 - case LPX_E_OK:
3.86 - return SOLVED;
3.87 + case LEMON_LPX(E_OK):
3.88 + solved = true;
3.89 default:
3.90 - return UNSOLVED;
3.91 - }
3.92 -
3.93 + solved = false;
3.94 + }
3.95 + } else {
3.96 + solved = false;
3.97 }
3.98 - return UNSOLVED;
3.99 +#if GLP_MAJOR_VERSION > 4 || (GLP_MAJOR_VERSION == 4 && GLP_MINOR_VERSION > 15)
3.100 + if (tmp != -1) {
3.101 + int tmpa[2];
3.102 + tmpa[1] = tmp;
3.103 + LEMON_lpx(del_cols)(lp, 1, tmpa);
3.104 + }
3.105 +#endif
3.106 + return solved ? SOLVED : UNSOLVED;
3.107 }
3.108
3.109
3.110 LpGlpk::SolutionStatus MipGlpk::_getMipStatus() const {
3.111
3.112 - if (lpx_get_status(lp)==LPX_OPT){
3.113 + if (LEMON_lpx(get_status)(lp)==LEMON_LPX(OPT)){
3.114 //Meg kell nezni: ha az LP is infinite, akkor ez is, ha az is
3.115 //infeasible, akkor ez is, de ez lehet maskepp is infeasible.
3.116 - int stat= lpx_mip_status(lp);
3.117 + int stat= LEMON_lpx(mip_status)(lp);
3.118
3.119 switch (stat) {
3.120 - case LPX_I_UNDEF://Undefined (no solve has been run yet)
3.121 + case LEMON_LPX(I_UNDEF)://Undefined (no solve has been run yet)
3.122 return UNDEFINED;
3.123 - case LPX_I_NOFEAS://There is no feasible integral solution
3.124 + case LEMON_LPX(I_NOFEAS)://There is no feasible integral solution
3.125 return INFEASIBLE;
3.126 - // case LPX_UNBND://Unbounded
3.127 + // case LEMON_LPX(UNBND)://Unbounded
3.128 // return INFINITE;
3.129 - case LPX_I_FEAS://Feasible
3.130 + case LEMON_LPX(I_FEAS)://Feasible
3.131 return FEASIBLE;
3.132 - case LPX_I_OPT://Feasible
3.133 + case LEMON_LPX(I_OPT)://Feasible
3.134 return OPTIMAL;
3.135 default:
3.136 - return UNDEFINED; //to avoid gcc warning
3.137 + return UNDEFINED; //to avoid gcc warning
3.138 //FIXME error
3.139 }
3.140 }
3.141 @@ -101,10 +139,10 @@
3.142 }
3.143
3.144 MipGlpk::Value MipGlpk::_getPrimal(int i) const {
3.145 - return lpx_mip_col_val(lp,i);
3.146 + return LEMON_glp(mip_col_val)(lp,i);
3.147 }
3.148
3.149 MipGlpk::Value MipGlpk::_getPrimalValue() const {
3.150 - return lpx_mip_obj_val(lp);
3.151 + return LEMON_glp(mip_obj_val)(lp);
3.152 }
3.153 } //END OF NAMESPACE LEMON
4.1 --- a/test/mip_test.cc Mon May 07 11:42:18 2007 +0000
4.2 +++ b/test/mip_test.cc Mon May 07 18:19:55 2007 +0000
4.3 @@ -41,7 +41,7 @@
4.4 lp.solve();
4.5 //int decimal,sign;
4.6 std::ostringstream buf;
4.7 - buf << "Primalstatus should be: " << int(stat)<<" and it is "<<int(lp.primalStatus());
4.8 + buf << "Primalstatus should be: " << int(stat)<<" and it is "<<int(lp.mipStatus());
4.9
4.10
4.11 // itoa(stat,buf1, 10);
4.12 @@ -81,13 +81,11 @@
4.13
4.14 //Constraints
4.15 mip.addRow(2*x1+x2 <=2);
4.16 - mip.addRow(x1-2*x2 <=0);
4.17 + mip.addRow(x1-2*x2 <=0);
4.18
4.19 //Nonnegativity of the variable x1
4.20 mip.colLowerBound(x1, 0);
4.21
4.22 -
4.23 -
4.24 //Maximization of x1
4.25 //over the triangle with vertices (0,0),(4/5,2/5),(0,2)
4.26 double expected_opt=4.0/5.0;