From b72e916c2cd0199913673a0ac1d399ba926c37a3 Mon Sep 17 00:00:00 2001 From: Thomas Roehr Date: Wed, 24 Jul 2024 15:57:16 +0200 Subject: [PATCH] Fix tests --- .github/workflows/test.yml | 2 +- src/algorithms/lp/CLPSolver.cpp | 93 ++++++++++++++++++- src/algorithms/lp/CLPSolver.hpp | 5 + .../test_MultiCommodityMinCostFlow.cpp | 1 + 4 files changed, 99 insertions(+), 2 deletions(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index a1e8ab1..706b23a 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -28,7 +28,7 @@ jobs: - name: Test run: docker run rock/${{ matrix.os }} /bin/bash -c - "source /home/docker/rock_test/env.sh; BOOST_TEST_CATCH_SYSTEM_ERRORS=\"no\" make -C /home/docker/rock_test/${{ matrix.package }}/build/test/graph_analysis-test --log_level=all" + "source /home/docker/rock_test/env.sh; BOOST_TEST_CATCH_SYSTEM_ERRORS=\"no\" /home/docker/rock_test/${{ matrix.package }}/build/test/graph_analysis-test --log_level=all" diff --git a/src/algorithms/lp/CLPSolver.cpp b/src/algorithms/lp/CLPSolver.cpp index 077efeb..b4c16f2 100644 --- a/src/algorithms/lp/CLPSolver.cpp +++ b/src/algorithms/lp/CLPSolver.cpp @@ -1,4 +1,6 @@ #include "CLPSolver.hpp" +#include +#include #include #include #include @@ -19,7 +21,80 @@ std::string CLPSolver::createSolverCommand() const return cmd; } -Solution CLPSolver::readBasicSolution(const std::string& filename) +Solution CLPSolver::readBasicSolution_v2(const std::string& filename) +{ + Solution solution; + std::ifstream solutionFile; + solutionFile.open(filename.c_str(), std::ios::in); + + std::string header; + getline(solutionFile, header); + boost::to_lower(header); + + std::vector splitLine; + boost::split(splitLine, header, boost::is_any_of("-"), boost::token_compress_on); + + std::string status = splitLine[0]; + boost::trim_if(status, boost::is_any_of(" ")); + + if(status == "optimal") + { + solution.setStatus(LPSolver::STATUS_OPTIMAL); + } else if(status == "infeasible") + { + solution.setStatus(LPSolver::STATUS_INFEASIBLE); + return solution; + } else { + solution.setStatus(LPSolver::STATUS_UNKNOWN); + } + + if(boost::contains(header, "objective value")) + { + // Optimal - objective value 6.00000000 + std::vector objectiveKeyValue; + std::string objective = splitLine[1]; + boost::trim_if(objective, boost::is_any_of(" ")); + boost::split(objectiveKeyValue, objective, boost::is_any_of(" "), boost::token_compress_on); + + // -- Parsing the header + double objectiveValue = 0; + try { + objectiveValue = boost::lexical_cast(objectiveKeyValue[2]); + } catch(const std::bad_cast& e) + { + LOG_WARN_S << "Failed to extract objective value from '" + + objective + "'"; + throw; + } + solution.setObjectiveValue(objectiveValue); + } + + std::string line; + while(std::getline(solutionFile, line)) + { + std::vector splitLine; + boost::trim_if(line, boost::is_any_of("\t ")); + // https://www.boost.org/doc/libs/1_49_0/doc/html/boost/algorithm/split_id820181.html + // token_compress_on: adjacent separators are merged together. Otherwise, every two separators delimit a token. + boost::split(splitLine, line, boost::is_any_of("\t "), boost::token_compress_on); + if(splitLine.empty()) + { + continue; + } + + { + if(splitLine.size() > 3 && boost::starts_with(splitLine[1], "x")) + { + solution.setColumnValue(splitLine[1], boost::lexical_cast(splitLine[2])); + } + } + } + + solutionFile.close(); + return solution; +} + +Solution CLPSolver::readBasicSolution_v1(const std::string& filename) { Solution solution; std::ifstream solutionFile; @@ -79,7 +154,23 @@ Solution CLPSolver::readBasicSolution(const std::string& filename) solutionFile.close(); return solution; +} + +Solution CLPSolver::readBasicSolution(const std::string& filename) +{ + Solution solution; + std::ifstream solutionFile; + solutionFile.open(filename.c_str(), std::ios::in); + + std::string line; + getline(solutionFile, line); + solutionFile.close(); + if(boost::contains(line, "-")) + { + return this->readBasicSolution_v2(filename); + } + return this->readBasicSolution_v1(filename); } } // end namespace lp diff --git a/src/algorithms/lp/CLPSolver.hpp b/src/algorithms/lp/CLPSolver.hpp index 747299b..beda7b1 100644 --- a/src/algorithms/lp/CLPSolver.hpp +++ b/src/algorithms/lp/CLPSolver.hpp @@ -19,7 +19,12 @@ class CLPSolver : public CommandlineSolver LPSolver::Type getSolverType() const override { return CLP_SOLVER; } std::string createSolverCommand() const override; + Solution readBasicSolution(const std::string& filename) override; + + Solution readBasicSolution_v1(const std::string& filename); + + Solution readBasicSolution_v2(const std::string& filename); }; } // end namespace lp diff --git a/test/algorithms/test_MultiCommodityMinCostFlow.cpp b/test/algorithms/test_MultiCommodityMinCostFlow.cpp index 9e2d145..811fe1e 100644 --- a/test/algorithms/test_MultiCommodityMinCostFlow.cpp +++ b/test/algorithms/test_MultiCommodityMinCostFlow.cpp @@ -107,6 +107,7 @@ BOOST_AUTO_TEST_CASE(multi_commodity_min_cost_flow_0) LPSolver::Status status; double cost = 0.0; { + BOOST_TEST_MESSAGE("SolverType: "<< LPSolver::TypeTxt[solverType]); std::string prefixPath("/tmp/graph_analysis-test-algorithms-multi_commodity_min_cost_flow_0"); MultiCommodityMinCostFlow minCostFlow(graph, commodities, solverType); checkSolverResult(status = minCostFlow.solve(prefixPath),