mirror of
https://github.com/Z3Prover/z3
synced 2025-04-10 19:27:06 +00:00
143 lines
3.1 KiB
C++
143 lines
3.1 KiB
C++
/*++
|
|
Copyright (c) 2010 Microsoft Corporation
|
|
|
|
Module Name:
|
|
|
|
expr_functors.cpp
|
|
|
|
Abstract:
|
|
|
|
Functors on expressions.
|
|
|
|
Author:
|
|
|
|
Nikolaj Bjorner (nbjorner) 2010-02-19
|
|
|
|
Revision History:
|
|
|
|
Hoisted from quant_elim.
|
|
|
|
--*/
|
|
|
|
#include "expr_functors.h"
|
|
|
|
// ----------
|
|
// check_pred
|
|
|
|
bool check_pred::operator()(expr* e) {
|
|
if (!m_visited.is_marked(e)) {
|
|
m_refs.push_back(e);
|
|
visit(e);
|
|
}
|
|
SASSERT(m_visited.is_marked(e));
|
|
return m_pred_holds.is_marked(e);
|
|
}
|
|
|
|
void check_pred::visit(expr* e) {
|
|
ptr_vector<expr> todo;
|
|
todo.push_back(e);
|
|
while (!todo.empty()) {
|
|
e = todo.back();
|
|
if (m_pred(e)) {
|
|
m_pred_holds.mark(e, true);
|
|
}
|
|
if (m_visited.is_marked(e)) {
|
|
todo.pop_back();
|
|
continue;
|
|
}
|
|
switch(e->get_kind()) {
|
|
case AST_APP: {
|
|
app* a = to_app(e);
|
|
bool all_visited = true;
|
|
unsigned num_args = a->get_num_args();
|
|
for (unsigned i = 0; i < num_args; ++i) {
|
|
expr* arg = a->get_arg(i);
|
|
if (!m_visited.is_marked(arg)) {
|
|
todo.push_back(arg);
|
|
all_visited = false;
|
|
}
|
|
else if (m_pred_holds.is_marked(arg)) {
|
|
m_pred_holds.mark(e, true);
|
|
}
|
|
}
|
|
if (all_visited) {
|
|
m_visited.mark(e, true);
|
|
todo.pop_back();
|
|
}
|
|
break;
|
|
}
|
|
case AST_QUANTIFIER: {
|
|
quantifier* q = to_quantifier(e);
|
|
expr* arg = q->get_expr();
|
|
if (m_visited.is_marked(arg)) {
|
|
todo.pop_back();
|
|
if (m_pred_holds.is_marked(arg)) {
|
|
m_pred_holds.mark(e, true);
|
|
}
|
|
m_visited.mark(e, true);
|
|
}
|
|
else {
|
|
todo.push_back(arg);
|
|
}
|
|
break;
|
|
}
|
|
case AST_VAR:
|
|
todo.pop_back();
|
|
m_visited.mark(e, true);
|
|
break;
|
|
default:
|
|
UNREACHABLE();
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
// ------------
|
|
// contains_app
|
|
|
|
|
|
bool contains_app::operator()(unsigned size, expr* const* es) {
|
|
for (unsigned i = 0; i < size; ++i) {
|
|
if ((*this)(es[i])) {
|
|
return true;
|
|
}
|
|
}
|
|
return false;
|
|
}
|
|
|
|
// -----------
|
|
// map_proc
|
|
|
|
void map_proc::reconstruct(app* a) {
|
|
m_args.reset();
|
|
bool is_new = false;
|
|
for (unsigned i = 0; i < a->get_num_args(); ++i) {
|
|
expr* e1 = a->get_arg(i);
|
|
expr* e2 = get_expr(e1);
|
|
m_args.push_back(e2);
|
|
if (e1 != e2) {
|
|
is_new = true;
|
|
}
|
|
}
|
|
if (is_new) {
|
|
expr* b = m.mk_app(a->get_decl(), m_args.size(), m_args.c_ptr());
|
|
m_map.insert(a, b, 0);
|
|
}
|
|
else {
|
|
m_map.insert(a, a, 0);
|
|
}
|
|
}
|
|
|
|
void map_proc::visit(quantifier* e) {
|
|
expr_ref q(m);
|
|
q = m.update_quantifier(e, get_expr(e->get_expr()));
|
|
m_map.insert(e, q, 0);
|
|
}
|
|
|
|
expr* map_proc::get_expr(expr* e) {
|
|
expr* result = 0;
|
|
proof* p = 0;
|
|
m_map.get(e, result, p);
|
|
return result;
|
|
}
|