3
0
Fork 0
mirror of https://github.com/Z3Prover/z3 synced 2025-05-07 15:55:46 +00:00

improving perf of mutex finding, revert semantics of 0 timeout to no-timeout. Issue #791

Signed-off-by: Nikolaj Bjorner <nbjorner@microsoft.com>
This commit is contained in:
Nikolaj Bjorner 2016-11-17 04:26:17 +02:00
parent e65d80dedd
commit e9db934f1a
10 changed files with 116 additions and 74 deletions

View file

@ -38,7 +38,8 @@ namespace opt {
m_c(c),
m_soft(soft),
m_weights(ws),
m_assertions(m) {
m_assertions(m),
m_trail(m) {
c.get_base_model(m_model);
SASSERT(m_model);
updt_params(c.params());
@ -152,6 +153,67 @@ namespace opt {
verbose_stream() << "(opt." << solver << " [" << l << ":" << u << "])\n";);
}
lbool maxsmt_solver_base::find_mutexes(obj_map<expr, rational>& new_soft) {
m_lower.reset();
for (unsigned i = 0; i < m_soft.size(); ++i) {
new_soft.insert(m_soft[i], m_weights[i]);
}
vector<expr_ref_vector> mutexes;
lbool is_sat = s().find_mutexes(m_soft, mutexes);
if (is_sat != l_true) {
return is_sat;
}
for (unsigned i = 0; i < mutexes.size(); ++i) {
process_mutex(mutexes[i], new_soft);
}
return l_true;
}
struct maxsmt_compare_soft {
obj_map<expr, rational> const& m_soft;
maxsmt_compare_soft(obj_map<expr, rational> const& soft): m_soft(soft) {}
bool operator()(expr* a, expr* b) const {
return m_soft.find(a) > m_soft.find(b);
}
};
void maxsmt_solver_base::process_mutex(expr_ref_vector& mutex, obj_map<expr, rational>& new_soft) {
TRACE("opt",
for (unsigned i = 0; i < mutex.size(); ++i) {
tout << mk_pp(mutex[i].get(), m) << " |-> " << new_soft.find(mutex[i].get()) << "\n";
});
if (mutex.size() <= 1) {
return;
}
maxsmt_compare_soft cmp(new_soft);
ptr_vector<expr> _mutex(mutex.size(), mutex.c_ptr());
std::sort(_mutex.begin(), _mutex.end(), cmp);
mutex.reset();
mutex.append(_mutex.size(), _mutex.c_ptr());
rational weight(0), sum1(0), sum2(0);
vector<rational> weights;
for (unsigned i = 0; i < mutex.size(); ++i) {
rational w = new_soft.find(mutex[i].get());
weights.push_back(w);
sum1 += w;
new_soft.remove(mutex[i].get());
}
for (unsigned i = mutex.size(); i > 0; ) {
--i;
expr_ref soft(m.mk_or(i+1, mutex.c_ptr()), m);
m_trail.push_back(soft);
rational w = weights[i];
weight = w - weight;
m_lower += weight*rational(i);
sum2 += weight*rational(i+1);
new_soft.insert(soft, weight);
for (; i > 0 && weights[i-1] == w; --i) {}
weight = w;
}
SASSERT(sum1 == sum2);
}
maxsmt::maxsmt(maxsat_context& c, unsigned index):
@ -310,4 +372,5 @@ namespace opt {
}
};