mirror of
https://github.com/Z3Prover/z3
synced 2025-04-23 17:15:31 +00:00
fix and coallesce clique functionality
Signed-off-by: Nikolaj Bjorner <nbjorner@microsoft.com>
This commit is contained in:
parent
1600823435
commit
ea601dd403
17 changed files with 361 additions and 119 deletions
|
@ -62,4 +62,4 @@ void qi_params::display(std::ostream & out) const {
|
|||
DISPLAY_PARAM(m_mbqi_trace);
|
||||
DISPLAY_PARAM(m_mbqi_force_template);
|
||||
DISPLAY_PARAM(m_mbqi_id);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -20,6 +20,8 @@ Revision History:
|
|||
#include "ast_util.h"
|
||||
#include "datatype_decl_plugin.h"
|
||||
#include "model_pp.h"
|
||||
#include "max_cliques.h"
|
||||
#include "stopwatch.h"
|
||||
|
||||
namespace smt {
|
||||
|
||||
|
@ -367,67 +369,46 @@ namespace smt {
|
|||
<< ")\n";
|
||||
}
|
||||
|
||||
struct neg_literal {
|
||||
unsigned negate(unsigned i) {
|
||||
return (~to_literal(i)).index();
|
||||
}
|
||||
};
|
||||
|
||||
lbool context::find_mutexes(expr_ref_vector const& vars, vector<expr_ref_vector>& mutexes) {
|
||||
uint_set lits;
|
||||
unsigned_vector ps;
|
||||
max_cliques<neg_literal> mc;
|
||||
expr_ref lit(m_manager);
|
||||
for (unsigned i = 0; i < vars.size(); ++i) {
|
||||
expr* n = vars[i];
|
||||
bool neg = m_manager.is_not(n, n);
|
||||
if (b_internalized(n)) {
|
||||
lits.insert(literal(get_bool_var(n), neg).index());
|
||||
ps.push_back(literal(get_bool_var(n), neg).index());
|
||||
}
|
||||
}
|
||||
while (!lits.empty()) {
|
||||
literal_vector mutex;
|
||||
uint_set other(lits);
|
||||
while (!other.empty()) {
|
||||
uint_set conseq;
|
||||
literal p = to_literal(*other.begin());
|
||||
other.remove(p.index());
|
||||
mutex.push_back(p);
|
||||
if (other.empty()) {
|
||||
break;
|
||||
for (unsigned i = 0; i < m_watches.size(); ++i) {
|
||||
watch_list & w = m_watches[i];
|
||||
for (literal const* it = w.begin_literals(), *end = w.end_literals(); it != end; ++it) {
|
||||
unsigned idx1 = (~to_literal(i)).index();
|
||||
unsigned idx2 = it->index();
|
||||
if (idx1 < idx2) {
|
||||
mc.add_edge(idx1, idx2);
|
||||
}
|
||||
get_reachable(p, other, conseq);
|
||||
other = conseq;
|
||||
}
|
||||
if (mutex.size() > 1) {
|
||||
expr_ref_vector mux(m_manager);
|
||||
for (unsigned i = 0; i < mutex.size(); ++i) {
|
||||
expr_ref e(m_manager);
|
||||
literal2expr(mutex[i], e);
|
||||
mux.push_back(e);
|
||||
}
|
||||
mutexes.push_back(mux);
|
||||
}
|
||||
for (unsigned i = 0; i < mutex.size(); ++i) {
|
||||
lits.remove(mutex[i].index());
|
||||
}
|
||||
}
|
||||
vector<unsigned_vector> _mutexes;
|
||||
mc.cliques(ps, _mutexes);
|
||||
for (unsigned i = 0; i < _mutexes.size(); ++i) {
|
||||
expr_ref_vector lits(m_manager);
|
||||
for (unsigned j = 0; j < _mutexes[i].size(); ++j) {
|
||||
literal2expr(to_literal(_mutexes[i][j]), lit);
|
||||
lits.push_back(lit);
|
||||
}
|
||||
mutexes.push_back(lits);
|
||||
}
|
||||
return l_true;
|
||||
}
|
||||
|
||||
void context::get_reachable(literal p, uint_set& goal, uint_set& reachable) {
|
||||
uint_set seen;
|
||||
literal_vector todo;
|
||||
todo.push_back(p);
|
||||
while (!todo.empty()) {
|
||||
// std::cout << "todo: " << todo.size() << "\n";
|
||||
p = todo.back();
|
||||
todo.pop_back();
|
||||
if (seen.contains(p.index())) {
|
||||
continue;
|
||||
}
|
||||
seen.insert(p.index());
|
||||
literal np = ~p;
|
||||
if (goal.contains(np.index())) {
|
||||
reachable.insert(np.index());
|
||||
}
|
||||
watch_list & w = m_watches[np.index()];
|
||||
todo.append(static_cast<unsigned>(w.end_literals() - w.begin_literals()), w.begin_literals());
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Validate, in a slow pass, that the current consequences are correctly
|
||||
// extracted.
|
||||
|
|
|
@ -1367,11 +1367,6 @@ namespace smt {
|
|||
void validate_consequences(expr_ref_vector const& assumptions, expr_ref_vector const& vars,
|
||||
expr_ref_vector const& conseq, expr_ref_vector const& unfixed);
|
||||
|
||||
/*
|
||||
\brief Auxiliry function for mutex finding.
|
||||
*/
|
||||
|
||||
void get_reachable(literal p, uint_set& goal, uint_set& reached);
|
||||
|
||||
public:
|
||||
context(ast_manager & m, smt_params & fp, params_ref const & p = params_ref());
|
||||
|
|
|
@ -194,6 +194,7 @@ namespace smt {
|
|||
}
|
||||
tout << "\n";);
|
||||
|
||||
max_generation = std::max(m_qm->get_generation(q), max_generation);
|
||||
add_instance(q, bindings, max_generation);
|
||||
return true;
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue