File: poly2lp.h

package info (click to toggle)
polymake 4.3-4
  • links: PTS, VCS
  • area: main
  • in suites: bullseye
  • size: 31,528 kB
  • sloc: cpp: 152,204; perl: 43,222; javascript: 30,700; ansic: 2,937; java: 2,654; python: 641; sh: 244; xml: 117; makefile: 62
file content (122 lines) | stat: -rw-r--r-- 3,941 bytes parent folder | download
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
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
/* Copyright (c) 1997-2020
   Ewgenij Gawrilow, Michael Joswig, and the polymake team
   Technische Universität Berlin, Germany
   https://polymake.org

   This program is free software; you can redistribute it and/or modify it
   under the terms of the GNU General Public License as published by the
   Free Software Foundation; either version 2, or (at your option) any
   later version: http://www.gnu.org/licenses/gpl.txt.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.
--------------------------------------------------------------------------------
*/

#ifndef __POLYMAKE_POLY2LP_H__
#define __POLYMAKE_POLY2LP_H__

#include "polymake/Rational.h"
#include "polymake/SparseMatrix.h"
#include "polymake/SparseVector.h"
#include "polymake/Array.h"
#include <fstream>

namespace polymake { namespace polytope {
namespace {

template <typename Vector>
void print_row(std::ostream& os,
               const std::string& tag,
               Int index,
               const GenericVector<Vector>& v,
               const Array<std::string>& variable_names,
               const char* relop = nullptr)
{
   if (v == unit_vector<typename Vector::element_type>(v.dim(),0)) // don't print the line " 0 >= -1 "
      return;
   auto e = entire(v.top());
   typename Vector::element_type free_term(0);
   if (!e.at_end() && e.index()==0) {
      free_term=*e;  ++e;
   }
   os << "  " << tag;
   if (tag != "obj") os << index;
   os << ":";

   while (!e.at_end()) {
      os << ' ' << std::setiosflags(std::ios::showpos) << convert_to<double>(*e) << std::resetiosflags(std::ios::showpos)
         << ' ' << variable_names[e.index()-1];
      ++e;
   }
   if (relop) {
      os << ' ' << relop << ' ' << convert_to<double>(-free_term);
   } else if (!is_zero(free_term)) {
      os << ' ' << std::setiosflags(std::ios::showpos) << convert_to<double>(free_term) << std::resetiosflags(std::ios::showpos);
   }
   os << '\n';
}
} // end anonymous namespace

template<typename Scalar=Rational>
void print_lp(BigObject p, BigObject lp, const bool maximize, std::ostream& os)
{
   const Int is_feasible=p.give("FEASIBLE");
   const SparseMatrix<Scalar> 
      IE = p.give("FACETS | INEQUALITIES"),
      EQ = p.lookup("AFFINE_HULL | EQUATIONS");
   const SparseVector<Scalar> LO = lp.give("LINEAR_OBJECTIVE");
   const Int n_variables = IE.cols()-1;

   if (!is_feasible)
      throw std::runtime_error("input is not FEASIBLE");

   Array<std::string> variable_names;
   if (lp.get_attachment("VARIABLE_NAMES") >> variable_names) {
      if (variable_names.size() != n_variables)
         throw std::runtime_error("dimension mismatch between the polytope and VARIABLE_NAMES");
   } else {
      variable_names.resize(n_variables);
      for (Int j=0; j < n_variables; ++j)
         variable_names[j]='x' + std::to_string(j+1);
   }

   Array<bool> integers = lp.get_attachment("INTEGER_VARIABLES");

   os << std::setprecision(16)
      << (maximize ? "MAXIMIZE\n" : "MINIMIZE\n");
   
   print_row(os, "obj", 0, LO, variable_names);

   os << "Subject To\n";
   for (auto ie=entire(rows(IE)); !ie.at_end(); ++ie) {
      print_row(os, "ie", ie.index(), *ie, variable_names, ">=");
   }

   for (auto eq=entire(rows(EQ)); !eq.at_end(); ++eq) {
      print_row(os, "eq", eq.index(), *eq, variable_names, "=");
   }

   os << "BOUNDS\n";
   for (Int i = 0; i < n_variables; ++i)
      os << "  " << variable_names[i] << " free\n"; 

   if (!integers.empty()) {
      os << "GENERAL\n";
      for (Int i = 0; i < integers.size(); ++i)
         if (integers[i]) os << "  " << variable_names[i] << '\n';
   }
   os << "END" << endl;
}

} }

#endif // __POLYMAKE_POLY2LP_H__

// Local Variables:
// mode:C++
// c-basic-offset:3
// indent-tabs-mode:nil
// End: