All Classes Namespaces Files Functions Variables Typedefs Enumerations Friends Macros Pages
ir_components.hpp
Go to the documentation of this file.
1 //=======================================================================
2 // Copyright (c) 2013 Piotr Wygocki
3 // 2014 Piotr Godlewski
4 //
5 // Distributed under the Boost Software License, Version 1.0. (See
6 // accompanying file LICENSE_1_0.txt or copy at
7 // http://www.boost.org/LICENSE_1_0.txt)
8 //=======================================================================
16 #ifndef PAAL_IR_COMPONENTS_HPP
17 #define PAAL_IR_COMPONENTS_HPP
18 
19 
21 #include "paal/lp/ids.hpp"
22 #include "paal/lp/lp_base.hpp"
23 #include "paal/lp/problem_type.hpp"
24 #include "paal/utils/floating.hpp"
25 #include "paal/utils/functors.hpp"
26 
27 #include <boost/optional.hpp>
28 #include <boost/range/iterator_range.hpp>
29 #include <boost/tuple/tuple.hpp>
30 
31 #include <cmath>
32 
33 namespace paal {
34 namespace ir {
35 
40  public:
45 
49  template <typename Problem, typename LP>
50  boost::optional<double> operator()(Problem &, const LP &lp,
51  lp::col_id col) {
52  double x = lp.get_col_value(col);
53  double r = std::round(x);
54  if (m_compare.e(x,r)) {
55  return r;
56  }
57  return boost::none;
58  }
59 
60  protected:
63 };
64 
70 template <int...> class round_condition_equals {
71  round_condition_equals() = delete;
72 };
73 
79 template <int arg, int... args>
81  args...> : public round_condition_equals<args...> {
82  public:
87 
90  template <typename Problem, typename LP>
91  boost::optional<double> operator()(Problem &, const LP &lp,
92  lp::col_id col) {
93  return get(lp, lp.get_col_value(col));
94  }
95 
96  protected:
98  template <typename LP>
99  boost::optional<double> get(const LP & lp, double x) {
100  if (this->m_compare.e(x, arg)) {
101  return double(arg);
102  } else {
104  }
105  }
106 };
107 
114 template <> class round_condition_equals<> {
115  public:
119  round_condition_equals(double epsilon = utils::compare<double>::default_epsilon()): m_compare(epsilon) { }
120 
121  protected:
123  template <typename LP> boost::optional<double> get(const LP &lp, double x) {
124  return boost::none;
125  }
126 
129 };
130 
136 template <typename Cond, typename F> class round_condition_to_fun {
137  public:
142  round_condition_to_fun(Cond c = Cond(), F f = F()) : m_cond(c), m_f(f) {}
143 
145  template <typename Problem, typename LP>
146  boost::optional<double> operator()(Problem &, const LP &lp,
147  lp::col_id col) {
148  double x = lp.get_col_value(col);
149  if (m_cond(x)) {
150  return m_f(x);
151  }
152  return boost::none;
153  }
154 
155  private:
156  Cond m_cond;
157  F m_f;
158 };
159 
164  public:
169  : m_bound(b), m_compare(epsilon) {}
170 
172  bool operator()(double x) { return m_compare.ge(x, m_bound); }
173 
174  private:
175  double m_bound;
176  const utils::compare<double> m_compare;
177 };
178 
185  public round_condition_to_fun<cond_bigger_equal_than, utils::return_one_functor> {
191 };
192 
198  template <typename Problem, typename LP>
199  lp::problem_type operator()(Problem &, LP &lp) {
200  return lp.solve_simplex(lp::PRIMAL);
201  }
202 };
203 
209  template <typename Problem, typename LP>
210  lp::problem_type operator()(Problem &, LP &lp) {
211  return lp.resolve_simplex(lp::PRIMAL);
212  }
213 };
214 
219  public:
224 
228  template <typename Problem, typename LP>
229  bool operator()(Problem &, const LP &lp) {
230  for (lp::col_id col : lp.get_columns()) {
231  double col_val = lp.get_col_value(col);
232  if (!m_compare.e(col_val, std::round(col_val))) {
233  return false;
234  }
235  }
236 
237  return true;
238  }
239 
240  protected:
243 };
244 
249  public:
251  relaxations_limit_condition(int limit = 1) : m_limit(limit) {}
252 
256  bool operator()(int relaxed) { return relaxed >= m_limit; }
257 
258  private:
259  int m_limit;
260 };
261 
262 class Init;
263 class RoundCondition;
264 class RelaxCondition;
265 class SetSolution;
266 class SolveLP;
267 class ResolveLP;
268 class StopCondition;
269 class RelaxationsLimit;
270 
271 using components = data_structures::components<
272  Init,
280 
284 template <typename... Args>
285 using IRcomponents = typename components::type<Args...>;
286 
290 template <typename... Args>
291 auto make_IRcomponents(Args &&... args)
292  ->decltype(components::make_components(std::forward<Args>(args)...)) {
293  return components::make_components(std::forward<Args>(args)...);
294 }
295 
296 } // ir
297 } // paal
298 
299 #endif // PAAL_IR_COMPONENTS_HPP
lp::problem_type operator()(Problem &, LP &lp)
Finds an extreme point solution to the LP.
Checks if the relaxations limit was reached.
boost::optional< double > operator()(Problem &, const LP &lp, lp::col_id col)
Rounds the column if its value is integral.
The common LP solvers base class. Responsible for:
Definition: lp_base.hpp:55
problem_type
LP problem type.
bool operator()(double x)
Checks if a variable is greater or equal than a fixed bound.
lp::problem_type operator()(Problem &, LP &lp)
Finds an extreme point solution to the LP.
Finds an extreme point solution to the LP.
boost::optional< double > operator()(Problem &, const LP &lp, lp::col_id col)
static type< special_decay_t< components >...> make_components(components &&...comps)
make function for components
Definition: components.hpp:497
bool operator()(int relaxed)
Checks if the relaxations limit was reached.
Column rounding component. Rounds a column if its value is equal to one of the template parameter val...
This structure can be passed on Names list and represents Name and the default type value...
Definition: components.hpp:33
This file contains set of simple useful functors or functor adapters.
const utils::compare< double > m_compare
Double comparison object.
boost::optional< double > operator()(Problem &, const LP &lp, lp::col_id col)
Rounds a column if its value satisfies a fixed condition.
Finds an extreme point solution to the LP.
Default stop condition component.
default_round_condition(double epsilon=utils::compare< double >::default_epsilon())
constructor takes epsilon used in double comparison.
Checks if a variable is greater or equal than a fixed bound.
Column rounding component. A variable is rounded up to 1, if it has value at least half in the soluti...
const utils::compare< double > m_compare
Double comparison object.
bool ge(T a, T b) const
greater equals
Definition: floating.hpp:43
Class for comparing floating point.
Definition: floating.hpp:26
Column rounding component. Rounds a column if its value satisfies a fixed condition. The column is rounded to a value defined by a fixed function.
typename components::type< Args...> IRcomponents
Iterative rounding components.
bool operator()(Problem &, const LP &lp)
Checks if the current LP solution has got only integer values.
const utils::compare< double > m_compare
Double comparison object.
relaxations_limit_condition(int limit=1)
Constructor.
const ColSet & get_columns() const
Definition: lp_base.hpp:216
double get_col_value(col_id col) const
Definition: lp_base.hpp:228
round_condition_to_fun(Cond c=Cond(), F f=F())
Constructor. Takes the rounding condition and the rounding function.
round_condition_equals(double epsilon=utils::compare< double >::default_epsilon())
constructor takes epsilon used in double comparison.
bool e(T a, T b) const
equals
Definition: floating.hpp:33
Default column rounding condition component.
round_condition_greater_than_half(double epsilon=utils::compare< double >::default_epsilon())
constructor takes epsilon used in double comparison.
round_condition_equals(double epsilon=utils::compare< double >::default_epsilon())
constructor takes epsilon used in double comparison.
auto make_IRcomponents(Args &&...args) -> decltype(components::make_components(std::forward< Args >(args)...))
Returns iterative rounding components.
default_stop_condition(double epsilon=utils::compare< double >::default_epsilon())
Constructor. Takes epsilon used in double comparison.
cond_bigger_equal_than(double b, double epsilon=utils::compare< double >::default_epsilon())
constructor takes epsilon used in double comparison.