3
0
Fork 0
mirror of https://github.com/Z3Prover/z3 synced 2025-04-06 17:44:08 +00:00

replace model_ref by model* in tg_project,

Signed-off-by: Nikolaj Bjorner <nbjorner@microsoft.com>
This commit is contained in:
Nikolaj Bjorner 2025-02-15 19:34:52 -08:00
parent eee96ec312
commit a703cf81b1
4 changed files with 55 additions and 23 deletions

View file

@ -471,7 +471,7 @@ namespace mbp {
t = a.mk_idiv(t, a.mk_numeral(d.m_div, is_int)); t = a.mk_idiv(t, a.mk_numeral(d.m_div, is_int));
else if (!d.m_div.is_one() && !is_int) else if (!d.m_div.is_one() && !is_int)
t = a.mk_div(t, a.mk_numeral(d.m_div, is_int)); t = a.mk_div(t, a.mk_numeral(d.m_div, is_int));
result.push_back(def(expr_ref(x, m), t)); result.push_back({ expr_ref(x, m), t });
} }
} }

View file

@ -29,10 +29,8 @@ namespace mbp {
bool euf_project_plugin::operator()(model& model, app_ref_vector& vars, expr_ref_vector& lits) { bool euf_project_plugin::operator()(model& model, app_ref_vector& vars, expr_ref_vector& lits) {
return false; return false;
} }
bool euf_project_plugin::project(model& model, app_ref_vector& vars, expr_ref_vector& lits, vector<def>& defs) { void euf_project_plugin::solve_eqs(model& model, app_ref_vector& vars, expr_ref_vector& lits, vector<def>& defs) {
if (vars.empty())
return false;
flatten_and(lits); flatten_and(lits);
expr_mark var_set; expr_mark var_set;
auto is_pure = [&](expr_mark& var_set, expr* v) { auto is_pure = [&](expr_mark& var_set, expr* v) {
@ -40,29 +38,37 @@ namespace mbp {
}; };
for (auto v : vars) for (auto v : vars)
var_set.mark(v, true); var_set.mark(v, true);
unsigned has_def = false;
#if 1
// solve trivial equations // solve trivial equations
for (auto e : lits) { for (auto e : lits) {
expr* x = nullptr, *y = nullptr; expr* x = nullptr, *y = nullptr;
if (m.is_eq(e, x, y) && var_set.is_marked(x) && is_pure(var_set, y)) { if (m.is_eq(e, x, y) && var_set.is_marked(x) && is_pure(var_set, y)) {
vars.erase(to_app(x)); vars.erase(to_app(x));
defs.push_back({ expr_ref(x, m), expr_ref(y, m) }); defs.push_back({ expr_ref(x, m), expr_ref(y, m) });
has_def = true;
} }
else if (m.is_eq(e, y, x) && var_set.is_marked(x) && is_pure(var_set, y)) { else if (m.is_eq(e, y, x) && var_set.is_marked(x) && is_pure(var_set, y)) {
vars.erase(to_app(x)); vars.erase(to_app(x));
defs.push_back({ expr_ref(x, m), expr_ref(y, m) }); defs.push_back({ expr_ref(x, m), expr_ref(y, m) });
has_def = true;
} }
} }
if (has_def) }
return true;
#endif bool euf_project_plugin::project(model& model, app_ref_vector& vars, expr_ref_vector& lits, vector<def>& defs) {
if (vars.empty())
return false;
unsigned sz = defs.size();
while (true) {
unsigned sz1 = defs.size();
solve_eqs(model, vars, lits, defs);
if (sz1 == defs.size())
break;
}
if (sz < defs.size())
return true;
// check if there is a variable of uninterp sort // check if there is a variable of uninterp sort
if (all_of(vars, [&](expr* v) { return !m.is_uninterp(v->get_sort()); })) if (all_of(vars, [&](expr* v) { return !m.is_uninterp(v->get_sort()); }))
return has_def; return false;
term_graph tg(m); term_graph tg(m);
tg.add_lits(lits); tg.add_lits(lits);
@ -70,16 +76,41 @@ namespace mbp {
if (m.is_uninterp(v->get_sort())) if (m.is_uninterp(v->get_sort()))
tg.add_var(v); tg.add_var(v);
// expr_ref_vector terms(m);
// now what: for (expr* f : subterms::all(lits))
/// walk all subterms of lits. if (!m.is_bool(f))
// push in partitions by value. terms.push_back(f);
// add equations from model
// compute repr from tg.
// // try to project on representatives:
tg.add_model_based_terms(model, terms);
unsigned j = 0;
for (unsigned i = 0; i < vars.size(); ++i) {
app* v = vars.get(i);
if (m.is_uninterp(v->get_sort())) {
expr* r = tg.rep_of(v);
if (r)
defs.push_back({ expr_ref(v, m), expr_ref(r, m) });
else
vars[j++] = v;
}
else
vars[j++] = v;
}
vars.shrink(j);
if (sz < defs.size())
return true;
// walk equivalence classes.
// try to unify with pure classes.
// try to build a fresh term using available signature
return has_def; return false;
} }
} }

View file

@ -13,6 +13,7 @@ Copyright (c) 2025 Microsoft Corporation
namespace mbp { namespace mbp {
class euf_project_plugin : public project_plugin { class euf_project_plugin : public project_plugin {
void solve_eqs(model& model, app_ref_vector& vars, expr_ref_vector& lits, vector<def>& defs);
public: public:
euf_project_plugin(ast_manager& m); euf_project_plugin(ast_manager& m);
~euf_project_plugin() override; ~euf_project_plugin() override;

View file

@ -1086,7 +1086,7 @@ class term_graph::projector {
u_map<expr *> m_root2rep; u_map<expr *> m_root2rep;
th_rewriter m_rewriter; th_rewriter m_rewriter;
model_ref m_model; model* m_model = nullptr;
expr_ref_vector m_pinned; // tracks expr in the maps expr_ref_vector m_pinned; // tracks expr in the maps
expr *mk_pure(term const &t) { expr *mk_pure(term const &t) {
@ -1454,7 +1454,7 @@ class term_graph::projector {
m_term2app.reset(); m_term2app.reset();
m_root2rep.reset(); m_root2rep.reset();
m_pinned.reset(); m_pinned.reset();
m_model.reset(); m_model = nullptr;
} }
expr_ref_vector project() { expr_ref_vector project() {