SMT-RAT  24.02
Toolbox for Strategic and Parallel Satisfiability-Modulo-Theories Solving
polynomials.h
Go to the documentation of this file.
1 #pragma once
2 
3 #include "../common.h"
5 #include <boost/intrusive/set.hpp>
6 #include "../OCApproximationStatistics.h"
7 
9 
10 using level_t = unsigned;
11 using id_t = unsigned;
12 
13 /**
14  * Refers to a polynomial.
15  */
16 struct PolyRef {
17  /// The level of the polynomial.
19  /// The id of the polynomial with respect to its level.
21  /// The base level of the polynomial.
23 };
24 inline bool operator<(const PolyRef& lhs, const PolyRef& rhs) {
25  return lhs.level < rhs.level || (lhs.level == rhs.level && lhs.id < rhs.id);
26 }
27 inline bool operator==(const PolyRef& lhs, const PolyRef& rhs) {
28  return lhs.level == rhs.level && lhs.id == rhs.id;
29 }
30 inline bool operator!=(const PolyRef& lhs, const PolyRef& rhs) {
31  return !(lhs == rhs);
32 }
33 inline std::ostream& operator<<(std::ostream& os, const PolyRef& data) {
34  os << "(" << data.level << " " << data.id << ")";
35  return os;
36 }
37 
40  carl::Relation relation;
41 };
42 inline bool operator<(const PolyConstraint& lhs, const PolyConstraint& rhs) {
43  return lhs.lhs < rhs.lhs || (lhs.lhs == rhs.lhs && lhs.relation < rhs.relation);
44 }
45 inline bool operator==(const PolyConstraint& lhs, const PolyConstraint& rhs) {
46  return lhs.lhs == rhs.lhs && lhs.relation == rhs.relation;
47 }
48 inline bool operator!=(const PolyConstraint& lhs, const PolyConstraint& rhs) {
49  return !(lhs == rhs);
50 }
51 inline std::ostream& operator<<(std::ostream& os, const PolyConstraint& data) {
52  os << "(" << data.lhs << " " << data.relation << " 0)";
53  return os;
54 }
55 
56 inline auto base_level(Polynomial poly) {
57  level_t lvl = 0;
58  auto vars = carl::variables(poly);
59  for (level_t i = 0; i < poly.context().variable_ordering().size(); i++) {
60  if (poly.context().variable_ordering()[i] == poly.main_var()) break;
61  if (vars.has(poly.context().variable_ordering()[i])) lvl = i+1;
62  }
63  return lvl;
64 }
65 
66 /**
67  * A pool for polynomials.
68  *
69  * The polynomials are stored in a table, that is, a list of lists of polynomials of a given level.
70  */
71 class PolyPool {
72  struct Element : public boost::intrusive::set_base_hook<> {
75  Element(Polynomial&& p, id_t i) : poly(p), id(i) {}
76  friend bool operator<(const Element& e1, const Element& e2) {
77  return e1.poly < e2.poly;
78  }
79  };
80  struct element_less {
81  bool operator()(const Polynomial& poly, const Element& element) const {
82  return poly < element.poly;
83  }
84  bool operator()(const Element& element, const Polynomial& poly) const {
85  return element.poly < poly;
86  }
87  };
88 
89  typedef boost::intrusive::set<Element> ElementSet;
90 
91  Polynomial::ContextType m_context;
93 
94  std::vector<std::vector<std::unique_ptr<Element>>> m_polys;
95  std::vector<ElementSet> m_poly_ids;
96 
97  inline PolyRef negative_poly_ref() const { return PolyRef {0, 0, 0}; }
98  inline PolyRef zero_poly_ref() const { return PolyRef {0, 1, 0}; }
99  inline PolyRef positive_poly_ref() const { return PolyRef {0, 2, 0}; }
103 
104 public:
105  /**
106  * Constructs a polynomial pool with respect to a variable ordering.
107  *
108  * @param var_order The variable ordering determining polynomial levels.
109  */
111  for (size_t i = 0; i < m_var_order.size(); i++) {
112  m_polys.emplace_back();
113  m_poly_ids.emplace_back();
114  } // why not use resize?
115  }
116 
117  const VariableOrdering& var_order() const { return m_var_order; }
118 
119  std::pair<PolyRef,bool> insert(const Polynomial& poly) {
120  auto npoly = poly.normalized();
121  bool signflip = poly.unit_part() < 0;
122  PolyRef ref;
123  assert(carl::level_of(npoly) <= std::numeric_limits<level_t>::max());
124  ref.level = (level_t)carl::level_of(npoly);
125  if (ref.level == 0) {
126  assert(carl::is_constant(poly));
127  if (carl::is_zero(poly)) return std::make_pair(zero_poly_ref(), signflip);
128  else if (carl::is_negative(poly.constant_part())) return std::make_pair(negative_poly_ref(), signflip);
129  else return std::make_pair(positive_poly_ref(), signflip);
130  }
131  ref.base_level = base_level(npoly);
132  assert(ref.level <= m_polys.size() && ref.level > 0);
133  typename ElementSet::insert_commit_data insert_data;
134  auto res = m_poly_ids[ref.level-1].insert_check(npoly, element_less(), insert_data);
135  if (!res.second) {
136  ref.id = res.first->id;
137  } else {
138  assert(m_polys[ref.level-1].size() <= std::numeric_limits<id_t>::max());
139  ref.id = (id_t)m_polys[ref.level-1].size();
140  m_polys[ref.level-1].push_back(std::make_unique<Element>(std::move(npoly), ref.id));
141  m_poly_ids[ref.level-1].insert_commit(*m_polys[ref.level-1].back(), insert_data);
142  #ifdef SMTRAT_DEVOPTION_Statistics
143  OCApproximationStatistics::get_instance().degree(poly.degree(m_var_order[ref.level-1]));
144  #endif
145  }
146  return std::make_pair(ref, signflip);
147  }
148 
150  return insert(poly).first;
151  }
152 
153  const Polynomial& get(const PolyRef& ref) const {
154  assert(ref.level <= m_polys.size());
155  if (ref.level == 0) {
156  assert(ref.id <=2);
157  if (ref.id == negative_poly_ref().id) return negative_poly;
158  else if (ref.id == zero_poly_ref().id) return zero_poly;
159  else return positive_poly;
160  }
161  assert(ref.id < m_polys[ref.level-1].size());
162  return m_polys[ref.level-1][ref.id]->poly;
163  }
164 
165  const Polynomial& operator()(const PolyRef& ref) const {
166  return get(ref);
167  }
168 
169  PolyConstraint insert(const Constraint& constraint) {
170  auto [poly,signflip] = insert(constraint.lhs());
171  auto rel = signflip ? carl::turn_around(constraint.relation()) : constraint.relation();
172  return PolyConstraint { poly, rel };
173  }
174 
175  PolyConstraint operator()(const Constraint& constraint) {
176  return insert(constraint);
177  }
178 
179  const Constraint get(const PolyConstraint& ref) const {
180  return Constraint(get(ref.lhs), ref.relation);
181  }
182 
183  const Constraint operator()(const PolyConstraint& ref) const {
184  return get(ref);
185  }
186 
187  bool known(const Polynomial& poly) const {
188  auto npoly = poly.normalized();
189  auto level = carl::level_of(npoly);
190  auto res = m_poly_ids[level-1].find(npoly, element_less());
191  return res != m_poly_ids[level-1].end();
192  }
193 
194  void clear_levels(size_t level) {
195  assert(level > 0);
196  if (level > m_polys.size()) return;
197  m_poly_ids.erase(m_poly_ids.begin() + (level - 1), m_poly_ids.end());
198  m_polys.erase(m_polys.begin() + (level - 1), m_polys.end());
199  }
200 
201  const Polynomial::ContextType& context() const {
202  return m_context;
203  }
204 
205  inline friend std::ostream& operator<<(std::ostream& os, const PolyPool& data) {
206  std::size_t lvl_id = 1;
207  for (const auto& lvl : data.m_polys) {
208  os << std::endl << lvl_id << ":: ";
209  for (const auto& p : lvl) {
210  os << p->id << ": " << p->poly << "; ";
211  }
212  lvl_id++;
213  }
214  return os;
215  }
216 };
217 
218 }
const Polynomial::ContextType & context() const
Definition: polynomials.h:201
const Polynomial & get(const PolyRef &ref) const
Definition: polynomials.h:153
PolyConstraint insert(const Constraint &constraint)
Definition: polynomials.h:169
const Polynomial & operator()(const PolyRef &ref) const
Definition: polynomials.h:165
boost::intrusive::set< Element > ElementSet
Definition: polynomials.h:89
PolyConstraint operator()(const Constraint &constraint)
Definition: polynomials.h:175
const Constraint get(const PolyConstraint &ref) const
Definition: polynomials.h:179
const VariableOrdering & var_order() const
Definition: polynomials.h:117
friend std::ostream & operator<<(std::ostream &os, const PolyPool &data)
Definition: polynomials.h:205
std::vector< std::vector< std::unique_ptr< Element > > > m_polys
Definition: polynomials.h:94
const VariableOrdering & m_var_order
Definition: polynomials.h:92
const Constraint operator()(const PolyConstraint &ref) const
Definition: polynomials.h:183
std::pair< PolyRef, bool > insert(const Polynomial &poly)
Definition: polynomials.h:119
std::vector< ElementSet > m_poly_ids
Definition: polynomials.h:95
PolyRef operator()(const Polynomial &poly)
Definition: polynomials.h:149
bool known(const Polynomial &poly) const
Definition: polynomials.h:187
PolyPool(const Polynomial::ContextType &context)
Constructs a polynomial pool with respect to a variable ordering.
Definition: polynomials.h:110
Main datastructures.
Definition: delineation.h:9
bool operator==(const TaggedIndexedRoot &lhs, const TaggedIndexedRoot &rhs)
Definition: delineation.h:24
std::ostream & operator<<(std::ostream &os, const TaggedIndexedRoot &data)
Definition: delineation.h:17
auto base_level(Polynomial poly)
Definition: polynomials.h:56
bool operator<(const TaggedIndexedRoot &lhs, const TaggedIndexedRoot &rhs)
Definition: delineation.h:27
bool operator!=(const PolyRef &lhs, const PolyRef &rhs)
Definition: polynomials.h:30
std::vector< carl::Variable > VariableOrdering
Definition: common.h:11
carl::ContextPolynomial< Rational > Polynomial
Definition: common.h:16
carl::BasicConstraint< Polynomial > Constraint
Definition: common.h:18
std::vector< carl::Variable > variable_ordering(const carl::QuantifierPrefix &quantifiers, const FormulaT &formula)
Calculates a variable ordering based on the given quantifier blocks and the given formula.
static size_t level_of(const VariableOrdering &order, const Pol &poly)
Definition: Backend.h:25
bool is_constant(const T &t)
Checks whether the constraint is constant, i.e.
std::vector< carl::Variable > vars(const std::pair< QuantifierType, std::vector< carl::Variable >> &p)
Definition: QEQuery.h:43
friend bool operator<(const Element &e1, const Element &e2)
Definition: polynomials.h:76
bool operator()(const Element &element, const Polynomial &poly) const
Definition: polynomials.h:84
bool operator()(const Polynomial &poly, const Element &element) const
Definition: polynomials.h:81
id_t id
The id of the polynomial with respect to its level.
Definition: polynomials.h:20
level_t level
The level of the polynomial.
Definition: polynomials.h:18
level_t base_level
The base level of the polynomial.
Definition: polynomials.h:22