diff --git a/src/math/polysat/saturation.h b/src/math/polysat/saturation.h index c21de0bd6..9b3b538be 100644 --- a/src/math/polysat/saturation.h +++ b/src/math/polysat/saturation.h @@ -38,9 +38,7 @@ namespace polysat { vector m_new_constraints; char const* m_rule = nullptr; - void set_rule(char const* r) { m_rule = r; } - - bool find_upper_bound(pvar x, signed_constraint& c, rational& bound); + void set_rule(char const* r) { m_rule = r; } void push_omega(pdd const& x, pdd const& y); void push_omega_bisect(pdd const& x, rational x_max, pdd const& y, rational y_max); diff --git a/src/math/polysat/ule_constraint.cpp b/src/math/polysat/ule_constraint.cpp index 08ed8f96d..27931168e 100644 --- a/src/math/polysat/ule_constraint.cpp +++ b/src/math/polysat/ule_constraint.cpp @@ -134,20 +134,22 @@ namespace polysat { v = p.var(); else if (q.is_unilinear()) v = q.var(); - if (v != null_var) { - signed_constraint sc(this, is_positive); - s.m_viable.intersect(v, sc); - rational val; - switch (s.m_viable.find_viable(v, val)) { - case dd::find_t::singleton: - s.propagate(v, val, sc); - break; - case dd::find_t::empty: - s.set_conflict(v); - break; - default: - break; - } + else + return; + + signed_constraint sc(this, is_positive); + if (!s.m_viable.intersect(v, sc)) + return; + rational val; + switch (s.m_viable.find_viable(v, val)) { + case dd::find_t::singleton: + s.propagate(v, val, sc); // TBD why is sc used as justification? It should be all of viable + break; + case dd::find_t::empty: + s.set_conflict(v); + break; + default: + break; } } diff --git a/src/math/polysat/viable.cpp b/src/math/polysat/viable.cpp index a8c5fc42e..14c2cb6d6 100644 --- a/src/math/polysat/viable.cpp +++ b/src/math/polysat/viable.cpp @@ -64,25 +64,29 @@ namespace polysat { m_trail.pop_back(); } - void viable::intersect(pvar v, signed_constraint const& c) { + bool viable::intersect(pvar v, signed_constraint const& c) { auto& fi = s.m_forbidden_intervals; entry* ne = alloc_entry(); - if (!fi.get_interval(c, v, ne->interval, ne->side_cond) || ne->interval.is_currently_empty()) + if (!fi.get_interval(c, v, ne->interval, ne->side_cond) || ne->interval.is_currently_empty()) { m_alloc.push_back(ne); + return false; + } else { ne->src = c; - intersect(v, ne); + return intersect(v, ne); } } - void viable::intersect(pvar v, entry* ne) { + bool viable::intersect(pvar v, entry* ne) { entry* e = m_viable[v]; - if (e && e->interval.is_full()) - return; + if (e && e->interval.is_full()) { + m_alloc.push_back(ne); + return false; + } if (ne->interval.is_currently_empty()) { m_alloc.push_back(ne); - return; + return false; } auto create_entry = [&]() { @@ -98,8 +102,6 @@ namespace polysat { e->remove_from(m_viable[v], e); }; - //LOG("intersect " << ne->interval); - if (!e) m_viable[v] = create_entry(); else { @@ -107,14 +109,14 @@ namespace polysat { do { if (e->interval.contains(ne->interval)) { m_alloc.push_back(ne); - return; + return false; } while (ne->interval.contains(e->interval)) { entry* n = e->next(); remove_entry(e); if (!m_viable[v]) { m_viable[v] = create_entry(); - return; + return true; } if (e == first) first = n; @@ -124,13 +126,13 @@ namespace polysat { if (e->interval.lo_val() > ne->interval.lo_val()) { if (first->prev()->interval.contains(ne->interval)) { m_alloc.push_back(ne); - return; + return false; } e->insert_before(create_entry()); if (e == first) m_viable[v] = e->prev(); SASSERT(well_formed(m_viable[v])); - return; + return true; } e = e->next(); } @@ -139,6 +141,7 @@ namespace polysat { first->insert_before(create_entry()); } SASSERT(well_formed(m_viable[v])); + return true; } bool viable::has_viable(pvar v) { diff --git a/src/math/polysat/viable.h b/src/math/polysat/viable.h index 20023da4f..18b259f14 100644 --- a/src/math/polysat/viable.h +++ b/src/math/polysat/viable.h @@ -44,7 +44,7 @@ namespace polysat { entry* alloc_entry(); - void intersect(pvar v, entry* e); + bool intersect(pvar v, entry* e); public: viable(solver& s); @@ -64,7 +64,7 @@ namespace polysat { * update state of viable for pvar v * based on affine constraints */ - void intersect(pvar v, signed_constraint const& c); + bool intersect(pvar v, signed_constraint const& c); /** * Check whether variable v has any viable values left according to m_viable.