3
0
Fork 0
mirror of https://github.com/Z3Prover/z3 synced 2025-06-04 13:21:22 +00:00

update for equivalences

Signed-off-by: Nikolaj Bjorner <nbjorner@microsoft.com>
This commit is contained in:
Nikolaj Bjorner 2017-07-28 10:30:23 -07:00
parent 6dbfdf3e9c
commit b2b2c636f8
5 changed files with 68 additions and 8 deletions

View file

@ -1739,6 +1739,25 @@ namespace sat {
SASSERT(validate_unit_propagation(p, r, l)); SASSERT(validate_unit_propagation(p, r, l));
} }
bool ba_solver::is_extended_binary(ext_justification_idx idx, literal_vector & r) {
constraint const& c = index2constraint(idx);
switch (c.tag()) {
case card_t: {
card const& ca = c.to_card();
if (ca.size() == ca.k() + 1 && ca.lit() == null_literal) {
r.reset();
for (literal l : ca) r.push_back(l);
return true;
}
else {
return false;
}
}
default:
return false;
}
}
void ba_solver::simplify(xor& x) { void ba_solver::simplify(xor& x) {
// no-op // no-op
} }
@ -2004,17 +2023,39 @@ namespace sat {
/** /**
\brief Lex on (glue, size) \brief Lex on (glue, size)
*/ */
struct constraint_glue_lt { struct constraint_glue_psm_lt {
bool operator()(ba_solver::constraint const * c1, ba_solver::constraint const * c2) const { bool operator()(ba_solver::constraint const * c1, ba_solver::constraint const * c2) const {
return return
(c1->glue() < c2->glue()) || (c1->glue() < c2->glue()) ||
(c1->glue() == c2->glue() && c1->size() < c2->size()); (c1->glue() == c2->glue() &&
(c1->psm() < c2->psm() ||
(c1->psm() == c2->psm() && c1->size() < c2->size())));
} }
}; };
void ba_solver::update_psm(constraint& c) const {
unsigned r = 0;
switch (c.tag()) {
case card_t:
for (literal l : c.to_card()) {
if (s().m_phase[l.var()] == (l.sign() ? NEG_PHASE : POS_PHASE)) ++r;
}
break;
case pb_t:
for (wliteral l : c.to_pb()) {
if (s().m_phase[l.second.var()] == (l.second.sign() ? NEG_PHASE : POS_PHASE)) ++r;
}
break;
default:
break;
}
c.set_psm(r);
}
void ba_solver::gc() { void ba_solver::gc() {
std::stable_sort(m_learned.begin(), m_learned.end(), constraint_glue_lt()); for (auto & c : m_learned) update_psm(*c);
gc_half("glue"); std::stable_sort(m_learned.begin(), m_learned.end(), constraint_glue_psm_lt());
gc_half("glue-psm");
cleanup_constraints(m_learned, true); cleanup_constraints(m_learned, true);
} }

View file

@ -62,12 +62,13 @@ namespace sat {
bool m_removed; bool m_removed;
literal m_lit; literal m_lit;
unsigned m_glue; unsigned m_glue;
unsigned m_psm;
unsigned m_size; unsigned m_size;
size_t m_obj_size; size_t m_obj_size;
bool m_learned; bool m_learned;
unsigned m_id; unsigned m_id;
public: public:
constraint(tag_t t, unsigned id, literal l, unsigned sz, size_t osz): m_tag(t), m_removed(false), m_lit(l), m_glue(0), m_size(sz), m_obj_size(osz), m_learned(false), m_id(id) {} constraint(tag_t t, unsigned id, literal l, unsigned sz, size_t osz): m_tag(t), m_removed(false), m_lit(l), m_glue(0), m_psm(0), m_size(sz), m_obj_size(osz), m_learned(false), m_id(id) {}
ext_constraint_idx index() const { return reinterpret_cast<ext_constraint_idx>(this); } ext_constraint_idx index() const { return reinterpret_cast<ext_constraint_idx>(this); }
unsigned id() const { return m_id; } unsigned id() const { return m_id; }
tag_t tag() const { return m_tag; } tag_t tag() const { return m_tag; }
@ -79,7 +80,9 @@ namespace sat {
void remove() { m_removed = true; } void remove() { m_removed = true; }
void nullify_literal() { m_lit = null_literal; } void nullify_literal() { m_lit = null_literal; }
unsigned glue() const { return m_glue; } unsigned glue() const { return m_glue; }
void set_glue(unsigned g) { m_glue = g; } void set_glue(unsigned g) { m_glue = g; }
unsigned psm() const { return m_psm; }
void set_psm(unsigned p) { m_psm = p; }
void set_learned(bool f) { m_learned = f; } void set_learned(bool f) { m_learned = f; }
bool learned() const { return m_learned; } bool learned() const { return m_learned; }
@ -265,6 +268,7 @@ namespace sat {
void subsumption(constraint& c1); void subsumption(constraint& c1);
void subsumption(card& c1); void subsumption(card& c1);
void gc_half(char const* _method); void gc_half(char const* _method);
void update_psm(constraint& c) const;
void mutex_reduction(); void mutex_reduction();
typedef vector<std::pair<rational, lp::var_index>> lhs_t; typedef vector<std::pair<rational, lp::var_index>> lhs_t;
@ -442,6 +446,7 @@ namespace sat {
virtual void pop_reinit(); virtual void pop_reinit();
virtual void gc(); virtual void gc();
virtual double get_reward(literal l, ext_justification_idx idx, literal_occs_fun& occs) const; virtual double get_reward(literal l, ext_justification_idx idx, literal_occs_fun& occs) const;
virtual bool is_extended_binary(ext_justification_idx idx, literal_vector & r);
ptr_vector<constraint> const & constraints() const { return m_constraints; } ptr_vector<constraint> const & constraints() const { return m_constraints; }

View file

@ -43,6 +43,7 @@ namespace sat {
virtual bool propagate(literal l, ext_constraint_idx idx) = 0; virtual bool propagate(literal l, ext_constraint_idx idx) = 0;
virtual double get_reward(literal l, ext_constraint_idx idx, literal_occs_fun& occs) const = 0; virtual double get_reward(literal l, ext_constraint_idx idx, literal_occs_fun& occs) const = 0;
virtual void get_antecedents(literal l, ext_justification_idx idx, literal_vector & r) = 0; virtual void get_antecedents(literal l, ext_justification_idx idx, literal_vector & r) = 0;
virtual bool is_extended_binary(ext_justification_idx idx, literal_vector & r) = 0;
virtual void asserted(literal l) = 0; virtual void asserted(literal l) = 0;
virtual check_result check() = 0; virtual check_result check() = 0;
virtual lbool resolve_conflict() { return l_undef; } // stores result in sat::solver::m_lemma virtual lbool resolve_conflict() { return l_undef; } // stores result in sat::solver::m_lemma

View file

@ -503,6 +503,7 @@ namespace sat {
// arcs are added in the opposite direction of implications. // arcs are added in the opposite direction of implications.
// So for implications l => u we add arcs u -> l // So for implications l => u we add arcs u -> l
void lookahead::init_arcs(literal l) { void lookahead::init_arcs(literal l) {
literal_vector lits;
literal_vector const& succ = m_binary[l.index()]; literal_vector const& succ = m_binary[l.index()];
for (unsigned i = 0; i < succ.size(); ++i) { for (unsigned i = 0; i < succ.size(); ++i) {
literal u = succ[i]; literal u = succ[i];
@ -512,6 +513,16 @@ namespace sat {
add_arc( u, l); add_arc( u, l);
} }
} }
for (auto w : m_watches[l.index()]) {
if (w.is_ext_constraint() && m_s.m_ext->is_extended_binary(w.get_ext_constraint_idx(), lits)) {
for (literal u : lits) {
if (u.index() > l.index() && is_stamped(u)) {
add_arc(~l, ~u);
add_arc( u, l);
}
}
}
}
} }
void lookahead::get_scc(literal v) { void lookahead::get_scc(literal v) {

View file

@ -33,10 +33,11 @@ namespace sat {
struct frame { struct frame {
unsigned m_lidx; unsigned m_lidx;
unsigned m_succ_idx;
bool m_first; bool m_first;
watched * m_it; watched * m_it;
watched * m_end; watched * m_end;
frame(unsigned lidx, watched * it, watched * end):m_lidx(lidx), m_first(true), m_it(it), m_end(end) {} frame(unsigned lidx, watched * it, watched * end, unsigned sidx = 0):m_lidx(lidx), m_succ_idx(sidx), m_first(true), m_it(it), m_end(end) {}
}; };
typedef svector<frame> frames; typedef svector<frame> frames;
@ -75,7 +76,7 @@ namespace sat {
index.resize(num_lits, UINT_MAX); index.resize(num_lits, UINT_MAX);
lowlink.resize(num_lits, UINT_MAX); lowlink.resize(num_lits, UINT_MAX);
in_s.resize(num_lits, false); in_s.resize(num_lits, false);
literal_vector roots; literal_vector roots, lits;
roots.resize(m_solver.num_vars(), null_literal); roots.resize(m_solver.num_vars(), null_literal);
unsigned next_index = 0; unsigned next_index = 0;
svector<frame> frames; svector<frame> frames;
@ -106,6 +107,7 @@ namespace sat {
frame & fr = frames.back(); frame & fr = frames.back();
unsigned l_idx = fr.m_lidx; unsigned l_idx = fr.m_lidx;
if (!fr.m_first) { if (!fr.m_first) {
SASSERT(fr.m_it->is_binary_clause());
// after visiting child // after visiting child
literal l2 = fr.m_it->get_literal(); literal l2 = fr.m_it->get_literal();
unsigned l2_idx = l2.index(); unsigned l2_idx = l2.index();