Debug("sets") << "[sets] in conflict = " << d_conflict << std::endl;
Assert( d_conflict ^ d_equalityEngine.consistent() );
if(d_conflict) return;
+ Debug("sets") << "[sets] is complete = " << isComplete() << std::endl;
}
- Debug("sets") << "[sets] is complete = " << isComplete() << std::endl;
if( (Theory::EFFORT_FULL || options::setsEagerLemmas() ) && !isComplete()) {
d_external.d_out->lemma(getLemma());
}
/******************** Model generation ********************/
/******************** Model generation ********************/
-typedef set<TNode> Elements;
-typedef hash_map<TNode, Elements, TNodeHashFunction> SettermElementsMap;
-
-const Elements& getElements(TNode setterm, SettermElementsMap& settermElementsMap) {
+const TheorySetsPrivate::Elements& TheorySetsPrivate::getElements
+(TNode setterm, SettermElementsMap& settermElementsMap) {
SettermElementsMap::const_iterator it = settermElementsMap.find(setterm);
- if(it == settermElementsMap.end() ) {
+ bool alreadyCalculated = (it != settermElementsMap.end());
+ if( !alreadyCalculated ) {
Kind k = setterm.getKind();
unsigned numChildren = setterm.getNumChildren();
return it->second;
}
-Node elementsToShape(Elements elements,
- TypeNode setType)
+
+void printSet(std::ostream& out, const std::set<TNode>& elements) {
+ out << "{ ";
+ std::copy(elements.begin(),
+ elements.end(),
+ std::ostream_iterator<TNode>(out, ", ")
+ );
+ out << " }";
+}
+
+
+void TheorySetsPrivate::checkModel(const SettermElementsMap& settermElementsMap, TNode S) const {
+
+ Debug("sets-model") << "[sets-model] checkModel(..., " << S << "): "
+ << std::endl;
+
+ Assert(S.getType().isSet());
+
+ Elements emptySetOfElements;
+ const Elements& saved =
+ d_equalityEngine.getRepresentative(S).getKind() == kind::EMPTYSET ?
+ emptySetOfElements :
+ settermElementsMap.find(d_equalityEngine.getRepresentative(S))->second;
+ Debug("sets-model") << "[sets-model] saved : ";
+ printSet(Debug("sets-model"), saved);
+ Debug("sets-model") << std::endl;
+
+ if(S.getNumChildren() == 2) {
+
+ Elements cur, left, right;
+ left = settermElementsMap.find(d_equalityEngine.getRepresentative(S[0]))->second;
+ right = settermElementsMap.find(d_equalityEngine.getRepresentative(S[1]))->second;
+ switch(S.getKind()) {
+ case kind::UNION:
+ if(left.size() >= right.size()) {
+ cur = left; cur.insert(right.begin(), right.end());
+ } else {
+ cur = right; cur.insert(left.begin(), left.end());
+ }
+ break;
+ case kind::INTERSECTION:
+ std::set_intersection(left.begin(), left.end(), right.begin(), right.end(),
+ std::inserter(cur, cur.begin()) );
+ break;
+ case kind::SETMINUS:
+ std::set_difference(left.begin(), left.end(), right.begin(), right.end(),
+ std::inserter(cur, cur.begin()) );
+ break;
+ default:
+ Unhandled();
+ }
+
+ Debug("sets-model") << "[sets-model] cur : ";
+ printSet(Debug("sets-model"), cur);
+ Debug("sets-model") << std::endl;
+
+ if(saved != cur) {
+ Debug("sets-model") << "[sets-model] *** ERRROR *** cur != saved "
+ << std::endl;
+ Debug("sets-model") << "[sets-model] FYI: "
+ << " [" << S << "] = " << d_equalityEngine.getRepresentative(S) << ", "
+ << " [" << S[0] << "] = " << d_equalityEngine.getRepresentative(S[0]) << ", "
+ << " [" << S[1] << "] = " << d_equalityEngine.getRepresentative(S[1]) << "\n";
+
+ }
+ Assert( saved == cur );
+ }
+}
+
+Node TheorySetsPrivate::elementsToShape(Elements elements, TypeNode setType) const
{
NodeManager* nm = NodeManager::currentNM();
if(elements.size() == 0) {
return nm->mkConst(EmptySet(nm->toType(setType)));
} else {
-
Elements::iterator it = elements.begin();
Node cur = SET_SINGLETON(*it);
while( ++it != elements.end() ) {
set<Node> terms;
- // Computer terms appearing assertions and shared terms
+ // Compute terms appearing assertions and shared terms
d_external.computeRelevantTerms(terms);
- // compute for each setterm elements that it contains
+ // Compute for each setterm elements that it contains
SettermElementsMap settermElementsMap;
TNode true_atom = NodeManager::currentNM()->mkConst<bool>(true);
TNode false_atom = NodeManager::currentNM()->mkConst<bool>(false);
m->assertEquality(shape, setterm, true);
m->assertRepresentative(shape);
}
+
+#ifdef CVC4_ASSERTIONS
+ BOOST_FOREACH(TNode term, terms) {
+ if( term.getType().isSet() ) {
+ checkModel(settermElementsMap, term);
+ }
+ }
+#endif
}
TheorySetsPrivate::Statistics::Statistics() :
d_checkTime("theory::sets::time") {
+
StatisticsRegistry::registerStat(&d_checkTime);
}
}
void TheorySetsPrivate::addToPending(Node n) {
+ Debug("sets-pending") << "[sets-pending] addToPending " << n << std::endl;
if(d_pendingEverInserted.find(n) == d_pendingEverInserted.end()) {
if(n.getKind() == kind::MEMBER) {
+ Debug("sets-pending") << "[sets-pending] \u2514 added to member queue"
+ << std::endl;
d_pending.push(n);
} else {
+ Debug("sets-pending") << "[sets-pending] \u2514 added to equality queue"
+ << std::endl;
Assert(n.getKind() == kind::EQUAL);
d_pendingDisequal.push(n);
}
- d_pendingEverInserted.insert(n);
}
}
bool TheorySetsPrivate::isComplete() {
- while(!d_pending.empty() && present(d_pending.front()))
+ while(!d_pending.empty() && present(d_pending.front())) {
+ Debug("sets-pending") << "[sets-pending] removing as already present: "
+ << d_pending.front() << std::endl;
d_pending.pop();
+ }
return d_pending.empty() && d_pendingDisequal.empty();
}
if(!d_pending.empty()) {
Node n = d_pending.front();
d_pending.pop();
+ d_pendingEverInserted.insert(n);
Assert(!present(n));
Assert(n.getKind() == kind::MEMBER);
} else {
Node n = d_pendingDisequal.front();
d_pendingDisequal.pop();
+ d_pendingEverInserted.insert(n);
Assert(n.getKind() == kind::EQUAL && n[0].getType().isSet());
Node x = NodeManager::currentNM()->mkSkolem("sde_$$", n[0].getType().getSetElementType());
Node l1 = MEMBER(x, n[0]), l2 = MEMBER(x, n[1]);
- // d_equalityEngine.addTerm(x);
- // d_equalityEngine.addTerm(l1);
- // d_equalityEngine.addTerm(l2);
- // d_terms.insert(x);
-
lemma = OR(n, AND(l1, NOT(l2)), AND(NOT(l1), l2));
}
--- /dev/null
+; EXPECT: sat
+
+; Observed behavior:
+; --check-model failed for set-term (union (z3f69 z3v151) (setenum z3v143))
+; with different set of elements in the model for representative and the node
+; itself.
+;
+; Issue:
+; The trouble with data structure being mainted to ensure that things
+; for which lemmas have been generated are not generated again. This
+; data structure (d_pendingEverInserted) needs to be user context
+; dependent. The bug was in the sequence of steps from requesting that
+; a lemma be generated to when it actually was. Sequence was:
+; addToPending (and also adds to pending ever inserted) ->
+; isComplete (might remove things from pending if requirment met in other ways) ->
+; getLemma (actually generated the lemma, if requirement not already met)
+;
+; Resolution:
+; adding terms to d_pendingEverInserted was moved from addToPending()
+; to getLemma().
+
+(set-logic QF_ALL_SUPPORTED)
+(set-info :status sat)
+(define-sort Elt () Int)
+(define-sort mySet () (Set Elt ))
+(define-fun smt_set_emp () mySet (as emptyset mySet))
+(define-fun smt_set_mem ((x Elt) (s mySet)) Bool (in x s))
+(define-fun smt_set_add ((s mySet) (x Elt)) mySet (union s (setenum x)))
+(define-fun smt_set_cup ((s1 mySet) (s2 mySet)) mySet (union s1 s2))
+(define-fun smt_set_cap ((s1 mySet) (s2 mySet)) mySet (intersection s1 s2))
+;(define-fun smt_set_com ((s mySet)) mySet ((_ map not) s))
+(define-fun smt_set_dif ((s1 mySet) (s2 mySet)) mySet (setminus s1 s2))
+;(define-fun smt_set_sub ((s1 mySet) (s2 mySet)) Bool (= smt_set_emp (smt_set_dif s1 s2)))
+(define-fun smt_set_sub ((s1 mySet) (s2 mySet)) Bool (subseteq s1 s2))
+
+(declare-fun z3v58 () Int)
+(declare-fun z3v59 () Int)
+(assert (distinct z3v58 z3v59))
+
+(declare-fun z3f60 (Int) Bool)
+(declare-fun z3v61 () Int)
+(declare-fun z3f62 (Int) Int)
+(declare-fun z3v63 () Int)
+(declare-fun z3v64 () Int)
+(declare-fun z3v67 () Int)
+(declare-fun z3f68 (Int) Int)
+(declare-fun z3f69 (Int) mySet)
+(declare-fun z3f70 (Int) mySet)
+(declare-fun z3f71 (Int) Bool)
+(declare-fun z3v90 () Int)
+(declare-fun z3v91 () Int)
+(declare-fun z3f92 (Int Int) Int)
+(declare-fun z3v140 () Int)
+(declare-fun z3v141 () Int)
+(declare-fun z3v142 () Int)
+(declare-fun z3v143 () Int)
+(declare-fun z3v144 () Int)
+(declare-fun z3v145 () Int)
+(declare-fun z3v147 () Int)
+(declare-fun z3v150 () Int)
+(declare-fun z3v151 () Int)
+(declare-fun z3v152 () Int)
+
+(assert (not (= (z3f69 z3v152)
+ (z3f69 z3v140))))
+
+(assert (= (z3f69 z3v151)
+ (smt_set_cup (z3f69 z3v141)
+ (z3f69 z3v140))))
+
+(assert (= (z3f69 z3v152)
+ (smt_set_cup (setenum z3v143) (z3f69 z3v151))))
+
+(assert (= (z3f70 z3v152)
+ (smt_set_cup (setenum z3v143) (z3f70 z3v151))))
+
+(assert (and
+ (= (z3f69 z3v142)
+ (smt_set_cup (setenum z3v143) (z3f69 z3v141)))
+ (= (z3f70 z3v142)
+ (smt_set_cup (setenum z3v143) (z3f70 z3v141)))
+ (= z3v142 (z3f92 z3v143 z3v141))
+ (= z3v142 z3v144)
+ (= (z3f62 z3v61) z3v61)
+ (= (z3f62 z3v63) z3v63)
+ )
+ )
+
+(check-sat)