1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89
|
#include "HCheckConfig.h"
#include "catch.hpp"
#include "ipm/ipx/ipx_status.h"
#include "ipm/ipx/lp_solver.h"
#include "lp_data/HConst.h"
#include "lp_data/HighsCallback.h"
#include "lp_data/HighsLp.h"
#include "lp_data/HighsStatus.h"
#include "parallel/HighsParallel.h"
// Example for using IPX from its C++ interface. The program solves the Netlib
// problem afiro.
#include <cmath>
#include <iostream>
#include "ipm/ipx/lp_solver.h"
const bool dev_run = false;
using Int = ipxint;
constexpr HighsInt num_var = 12;
constexpr HighsInt num_constr = 9;
const double obj[] = {-0.2194, 0.0, 0.0, 0.0, 0.0, 0.0,
0.0, 0.0, -0.32, -0.5564, 0.6, -0.48};
const double lb[num_var] = {0.0};
const double ub[] = {80.0, 283.303, 283.303, 312.813, 349.187, INFINITY,
INFINITY, INFINITY, 57.201, 500.0, 500.501, 357.501};
// Constraint matrix in CSC format with 0-based indexing.
const HighsInt Ap[] = {0, 2, 6, 10, 14, 18, 20, 22, 24, 26, 28, 30, 32};
const HighsInt Ai[] = {0, 5, 1, 6, 7, 8, 2, 6, 7, 8, 3, 6, 7, 8, 4, 6,
7, 8, 1, 2, 2, 3, 2, 4, 0, 6, 0, 5, 2, 5, 5, 7};
const double Ax[] = {-1.0, 0.301, 1.0, -1.0, 0.301, 1.06, 1.0,
-1.0, 0.313, 1.06, 1.0, -1.0, 0.313, 0.96,
1.0, -1.0, 0.326, 0.86, -1.0, 0.99078, 1.00922,
-1.0, 1.01802, -1.0, 1.4, 1.0, 0.109, -1.0,
-0.419111, 1.0, 1.4, -1.0};
const double rhs[] = {0.0, 80.0, 0.0, 0.0, 0.0, 0.0, 0.0, 44.0, 300.0};
const char constr_type[] = {'<', '<', '=', '<', '<', '=', '<', '<', '<'};
TEST_CASE("test-ipx", "[highs_ipx]") {
ipx::LpSolver lps;
ipx::Parameters parameters;
if (!dev_run) parameters.display = 0;
parameters.highs_logging = false;
lps.SetParameters(parameters);
// Solve the LP.
Int load_status = lps.LoadModel(num_var, obj, lb, ub, num_constr, Ap, Ai, Ax,
rhs, constr_type);
REQUIRE(load_status == 0);
highs::parallel::initialize_scheduler();
HighsCallback callback;
// Set pointer to null callback
lps.SetCallback(&callback);
Int status = lps.Solve();
bool is_solved = status == IPX_STATUS_solved;
REQUIRE(is_solved);
// Get solver and solution information.
ipx::Info info = lps.GetInfo();
// Get the interior solution (available if IPM was started).
double x[num_var], xl[num_var], xu[num_var], slack[num_constr];
double y[num_constr], zl[num_var], zu[num_var];
lps.GetInteriorSolution(x, xl, xu, slack, y, zl, zu);
REQUIRE(fabs(x[11] - 339.9) < 1.0);
REQUIRE(fabs(xl[11] - 339.94) < 1.0);
REQUIRE(fabs(xu[11] - 17.55) < 1.0);
REQUIRE(fabs(slack[8] - 234.76) < 1.0);
REQUIRE(fabs(y[8]) < 1.0);
REQUIRE(fabs(zl[11]) < 1.0);
REQUIRE(fabs(zu[11]) < 1.0);
// Get the basic solution (available if crossover terminated without error).
double ipx_col_value[num_var], ipx_row_value[num_constr];
double ipx_row_dual[num_constr], ipx_col_dual[num_var];
Int ipx_row_status[num_constr], ipx_col_status[num_var];
lps.GetBasicSolution(ipx_col_value, ipx_row_value, ipx_row_dual, ipx_col_dual,
ipx_row_status, ipx_col_status);
REQUIRE(fabs(ipx_col_value[11] - 339.9) < 1);
(void)(info); // surpress unused variable.
}
|