summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorAndrew Reynolds <andrew.j.reynolds@gmail.com>2020-02-22 10:07:44 -0600
committerGitHub <noreply@github.com>2020-02-22 10:07:44 -0600
commit25d2ed390bf5ad825fadbc4ed21676100b01de68 (patch)
tree156852139ee7a5bc5e42d1fc2564c75b291216fe /src
parent9b20af281db3e77a25540305dfb73cbe56519f75 (diff)
Move check memberships to reg exp solver (#3793)
There was previously a function in TheoryStrings to make the proper call to checkMembership. In the refactored code, this is no longer necessary and the interface to RegExp can be simplified.
Diffstat (limited to 'src')
-rw-r--r--src/theory/strings/extf_solver.cpp5
-rw-r--r--src/theory/strings/extf_solver.h5
-rw-r--r--src/theory/strings/regexp_solver.cpp33
-rw-r--r--src/theory/strings/regexp_solver.h17
-rw-r--r--src/theory/strings/theory_strings.cpp36
-rw-r--r--src/theory/strings/theory_strings.h11
6 files changed, 62 insertions, 45 deletions
diff --git a/src/theory/strings/extf_solver.cpp b/src/theory/strings/extf_solver.cpp
index e22528490..6ab74cf9a 100644
--- a/src/theory/strings/extf_solver.cpp
+++ b/src/theory/strings/extf_solver.cpp
@@ -668,6 +668,11 @@ const std::map<Node, ExtfInfoTmp>& ExtfSolver::getInfo() const
}
bool ExtfSolver::hasExtendedFunctions() const { return d_hasExtf.get(); }
+std::vector<Node> ExtfSolver::getActive(Kind k) const
+{
+ return d_extt->getActive(k);
+}
+
} // namespace strings
} // namespace theory
} // namespace CVC4
diff --git a/src/theory/strings/extf_solver.h b/src/theory/strings/extf_solver.h
index e0e41bc3d..4c848f430 100644
--- a/src/theory/strings/extf_solver.h
+++ b/src/theory/strings/extf_solver.h
@@ -145,6 +145,11 @@ class ExtfSolver
const std::map<Node, ExtfInfoTmp>& getInfo() const;
/** Are there any active extended functions? */
bool hasExtendedFunctions() const;
+ /**
+ * Get the function applications of kind k that are active in the current
+ * context (see ExtTheory::getActive).
+ */
+ std::vector<Node> getActive(Kind k) const;
private:
/** do reduction
diff --git a/src/theory/strings/regexp_solver.cpp b/src/theory/strings/regexp_solver.cpp
index e4fe2cf17..5b41feacb 100644
--- a/src/theory/strings/regexp_solver.cpp
+++ b/src/theory/strings/regexp_solver.cpp
@@ -36,11 +36,13 @@ namespace strings {
RegExpSolver::RegExpSolver(TheoryStrings& p,
SolverState& s,
InferenceManager& im,
+ ExtfSolver& es,
context::Context* c,
context::UserContext* u)
: d_parent(p),
d_state(s),
d_im(im),
+ d_esolver(es),
d_regexp_ucached(u),
d_regexp_ccached(c),
d_processed_memberships(c)
@@ -57,6 +59,37 @@ Node RegExpSolver::mkAnd(Node c1, Node c2)
return NodeManager::currentNM()->mkNode(AND, c1, c2);
}
+void RegExpSolver::checkMemberships()
+{
+ // add the memberships
+ std::vector<Node> mems = d_esolver.getActive(STRING_IN_REGEXP);
+ // maps representatives to regular expression memberships in that class
+ std::map<Node, std::vector<Node> > assertedMems;
+ const std::map<Node, ExtfInfoTmp>& einfo = d_esolver.getInfo();
+ std::map<Node, ExtfInfoTmp>::const_iterator it;
+ for (unsigned i = 0; i < mems.size(); i++)
+ {
+ Node n = mems[i];
+ Assert(n.getKind() == STRING_IN_REGEXP);
+ it = einfo.find(n);
+ Assert(it != einfo.end());
+ if (!it->second.d_const.isNull())
+ {
+ bool pol = it->second.d_const.getConst<bool>();
+ Trace("strings-process-debug")
+ << " add membership : " << n << ", pol = " << pol << std::endl;
+ Node r = d_state.getRepresentative(n[0]);
+ assertedMems[r].push_back(pol ? n : n.negate());
+ }
+ else
+ {
+ Trace("strings-process-debug")
+ << " irrelevant (non-asserted) membership : " << n << std::endl;
+ }
+ }
+ check(assertedMems);
+}
+
void RegExpSolver::check(const std::map<Node, std::vector<Node> >& mems)
{
bool addedLemma = false;
diff --git a/src/theory/strings/regexp_solver.h b/src/theory/strings/regexp_solver.h
index a43ea516a..4880af905 100644
--- a/src/theory/strings/regexp_solver.h
+++ b/src/theory/strings/regexp_solver.h
@@ -23,6 +23,7 @@
#include "context/cdlist.h"
#include "context/context.h"
#include "expr/node.h"
+#include "theory/strings/extf_solver.h"
#include "theory/strings/inference_manager.h"
#include "theory/strings/regexp_operation.h"
#include "theory/strings/solver_state.h"
@@ -47,10 +48,22 @@ class RegExpSolver
RegExpSolver(TheoryStrings& p,
SolverState& s,
InferenceManager& im,
+ ExtfSolver& es,
context::Context* c,
context::UserContext* u);
~RegExpSolver() {}
+ /** check regular expression memberships
+ *
+ * This checks the satisfiability of all regular expression memberships
+ * of the form (not) s in R. We use various heuristic techniques based on
+ * unrolling, combined with techniques from Liang et al, "A Decision Procedure
+ * for Regular Membership and Length Constraints over Unbounded Strings",
+ * FroCoS 2015.
+ */
+ void checkMemberships();
+
+ private:
/** check
*
* Tells this solver to check whether the regular expressions in mems
@@ -63,8 +76,6 @@ class RegExpSolver
* engine of the theory of strings.
*/
void check(const std::map<Node, std::vector<Node>>& mems);
-
- private:
/**
* Check memberships in equivalence class for regular expression
* inclusion.
@@ -106,6 +117,8 @@ class RegExpSolver
SolverState& d_state;
/** the output channel of the parent of this object */
InferenceManager& d_im;
+ /** reference to the extended function solver of the parent */
+ ExtfSolver& d_esolver;
// check membership constraints
Node mkAnd(Node c1, Node c2);
/**
diff --git a/src/theory/strings/theory_strings.cpp b/src/theory/strings/theory_strings.cpp
index 5be2f96d4..d3d75a98d 100644
--- a/src/theory/strings/theory_strings.cpp
+++ b/src/theory/strings/theory_strings.cpp
@@ -79,7 +79,7 @@ TheoryStrings::TheoryStrings(context::Context* c,
d_bsolver(c, u, d_state, d_im),
d_csolver(c, u, d_state, d_im, d_sk_cache, d_bsolver),
d_esolver(nullptr),
- d_regexp_solver(*this, d_state, d_im, c, u),
+ d_rsolver(nullptr),
d_stringsFmf(c, u, valuation, d_sk_cache),
d_strategy_init(false)
{
@@ -87,6 +87,7 @@ TheoryStrings::TheoryStrings(context::Context* c,
ExtTheory* extt = getExtTheory();
d_esolver.reset(new ExtfSolver(
c, u, d_state, d_im, d_sk_cache, d_bsolver, d_csolver, extt));
+ d_rsolver.reset(new RegExpSolver(*this, d_state, d_im, *d_esolver, c, u));
getExtTheory()->addFunctionKind(kind::STRING_SUBSTR);
getExtTheory()->addFunctionKind(kind::STRING_STRIDOF);
getExtTheory()->addFunctionKind(kind::STRING_ITOS);
@@ -726,37 +727,6 @@ bool TheoryStrings::needsCheckLastEffort() {
return false;
}
-void TheoryStrings::checkMemberships()
-{
- // add the memberships
- std::vector<Node> mems = getExtTheory()->getActive(kind::STRING_IN_REGEXP);
- // maps representatives to regular expression memberships in that class
- std::map<Node, std::vector<Node> > assertedMems;
- const std::map<Node, ExtfInfoTmp>& einfo = d_esolver->getInfo();
- std::map<Node, ExtfInfoTmp>::const_iterator it;
- for (unsigned i = 0; i < mems.size(); i++)
- {
- Node n = mems[i];
- Assert(n.getKind() == STRING_IN_REGEXP);
- it = einfo.find(n);
- Assert(it != einfo.end());
- if (!it->second.d_const.isNull())
- {
- bool pol = it->second.d_const.getConst<bool>();
- Trace("strings-process-debug")
- << " add membership : " << n << ", pol = " << pol << std::endl;
- Node r = d_state.getRepresentative(n[0]);
- assertedMems[r].push_back(pol ? n : n.negate());
- }
- else
- {
- Trace("strings-process-debug")
- << " irrelevant (non-asserted) membership : " << n << std::endl;
- }
- }
- d_regexp_solver.check(assertedMems);
-}
-
/** Conflict when merging two constants */
void TheoryStrings::conflict(TNode a, TNode b){
if (!d_state.isInConflict())
@@ -1223,7 +1193,7 @@ void TheoryStrings::runInferStep(InferStep s, int effort)
case CHECK_LENGTH_EQC: d_csolver.checkLengthsEqc(); break;
case CHECK_REGISTER_TERMS_NF: checkRegisterTermsNormalForms(); break;
case CHECK_EXTF_REDUCTION: d_esolver->checkExtfReductions(effort); break;
- case CHECK_MEMBERSHIP: checkMemberships(); break;
+ case CHECK_MEMBERSHIP: d_rsolver->checkMemberships(); break;
case CHECK_CARDINALITY: d_bsolver.checkCardinality(); break;
default: Unreachable(); break;
}
diff --git a/src/theory/strings/theory_strings.h b/src/theory/strings/theory_strings.h
index f40af6e67..e0fca1b2e 100644
--- a/src/theory/strings/theory_strings.h
+++ b/src/theory/strings/theory_strings.h
@@ -344,7 +344,7 @@ private:
*/
std::unique_ptr<ExtfSolver> d_esolver;
/** regular expression solver module */
- RegExpSolver d_regexp_solver;
+ std::unique_ptr<RegExpSolver> d_rsolver;
/** regular expression elimination module */
RegExpElimination d_regexp_elim;
/** Strings finite model finding decision strategy */
@@ -392,15 +392,6 @@ private:
* there does not exist a term of the form str.len(si) in the current context.
*/
void checkRegisterTermsNormalForms();
- /** check regular expression memberships
- *
- * This checks the satisfiability of all regular expression memberships
- * of the form (not) s in R. We use various heuristic techniques based on
- * unrolling, combined with techniques from Liang et al, "A Decision Procedure
- * for Regular Membership and Length Constraints over Unbounded Strings",
- * FroCoS 2015.
- */
- void checkMemberships();
//-----------------------end inference steps
//-----------------------representation of the strategy
generated by cgit on debian on lair
contact matthew@masot.net with questions or feedback