00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
00026 
00027 
00028 
00029 #ifndef DOXYGEN
00030 #include "variable.h"
00031 #endif
00032 
00033 #ifndef _cvc3__include__clause_h_
00034 #define _cvc3__include__clause_h_
00035 
00036 namespace CVC3 {
00037 
00038   class Clause;
00039   class ClauseOwner;
00040   class TheoryCore;
00041 
00042   class ClauseValue {
00043     friend class Clause;
00044   private:
00045 
00046     int d_refcount;
00047 
00048     int d_refcountOwner;
00049     
00050     Theorem d_thm;
00051     
00052     int d_scope;
00053     
00054     
00055     std::vector<Literal> d_literals;
00056     
00057     ClauseValue(const ClauseValue& c); 
00058     ClauseValue& operator=(const ClauseValue& c) { return *this; }
00059     
00060     
00061     size_t d_wp[2];
00062     
00063     
00064     
00065     int d_dir[2];
00066     
00067     CDO<bool> d_sat;
00068     
00069     bool d_deleted;
00070     
00071     IF_DEBUG(std::string d_file; int d_line);
00072     
00073     
00074     ClauseValue(TheoryCore* core, VariableManager* vm,
00075     const Theorem& clause, int scope);
00076   public:
00077     
00078     ~ClauseValue();
00079       
00080   }; 
00081 
00082 
00083   class Clause {
00084   private:
00085     friend class ClauseOwner;
00086 
00087     ClauseValue* d_clause;
00088 
00089     int& countOwner() {
00090       DebugAssert(d_clause != NULL, "");
00091       return d_clause->d_refcountOwner;
00092     }
00093   public:
00094     Clause(): d_clause(NULL) { }
00095     
00096     Clause(TheoryCore* core, VariableManager* vm, const Theorem& clause,
00097            int scope, const std::string& file = "", int line = 0)
00098       : d_clause(new ClauseValue(core, vm, clause, scope)) {
00099       d_clause->d_refcount++;
00100       IF_DEBUG(d_clause->d_file = file; d_clause->d_line=line);
00101     }
00102     
00103     Clause(const Clause& c): d_clause(c.d_clause) {
00104       if(d_clause != NULL) d_clause->d_refcount++;
00105     }
00106     
00107     ~Clause();
00108     
00109     Clause& operator=(const Clause& c);
00110 
00111     bool isNull() const { return d_clause == NULL; }
00112     
00113     size_t size() const {
00114       return (d_clause == NULL)? 0 : d_clause->d_literals.size();
00115     }
00116     
00117     const Theorem& getTheorem() const {
00118       DebugAssert(!isNull(), "Clause::getTheorem(): Null Clause");
00119       return d_clause->d_thm;
00120     }
00121     
00122     int getScope() const {
00123       if(isNull()) return 0;
00124       else return d_clause->d_scope;
00125     }
00126     
00127     const Literal& getLiteral(size_t i) const {
00128       DebugAssert(!isNull(), "Clause::getLiteral(): Null Clause");
00129       DebugAssert(i < size(), 
00130       "Clause::getLiteral(" + int2string(i)
00131       + "): i >= size = " + int2string(size()));
00132       return d_clause->d_literals[i];
00133     }
00134     
00135     const Literal& operator[](size_t i) const { return getLiteral(i); }
00136 
00137     
00138     const std::vector<Literal>& getLiterals() const {
00139       DebugAssert(!isNull(), "Clause::getLiterals(): Null Clause");
00140       return d_clause->d_literals;
00141     }
00142     
00143     size_t wp(int i) const {
00144       DebugAssert(!isNull(), "Clause::wp(i): Null Clause");
00145       DebugAssert(i==0 || i==1, 
00146       "wp(i): Watch pointer index is out of bounds: i = "
00147       + int2string(i));
00148       return d_clause->d_wp[i];
00149     }
00150     
00151     const Literal& watched(int i) const { return getLiteral(wp(i)); }
00152     
00153     size_t wp(int i, size_t l) const {
00154       DebugAssert(!isNull(), "Clause::wp(i,l): Null Clause");
00155       DebugAssert(i==0 || i==1, 
00156       "wp(i,l): Watch pointer index is out of bounds: i = "
00157       + int2string(i));
00158       DebugAssert(l < size(), "Clause::wp(i = " + int2string(i)
00159       + ", l = " + int2string(l)
00160       + "): l >= size() = " + int2string(size()));
00161       TRACE("clauses", " **clauses** UPDATE wp(idx="
00162       +int2string(i)+", l="+int2string(l),
00163       ")\n  clause #: ", id());
00164       d_clause->d_wp[i] = l;
00165       return l;
00166     }
00167     
00168     int dir(int i) const {
00169       DebugAssert(!isNull(), "Clause::dir(i): Null Clause");
00170       DebugAssert(i==0 || i==1, 
00171       "dir(i): Watch pointer index is out of bounds: i = "
00172       + int2string(i));
00173       return d_clause->d_dir[i];
00174     }
00175     
00176     int dir(int i, int d) const {
00177       DebugAssert(!isNull(), "Clause::dir(i,d): Null Clause");
00178       DebugAssert(i==0 || i==1, 
00179       "dir(i="+int2string(i)+",d="+int2string(d)
00180       +"): Watch pointer index is out of bounds");
00181       DebugAssert(d==1 || d==-1, "dir(i="+int2string(i)+",d="+int2string(d)
00182       +"): Direction is out of bounds");
00183       d_clause->d_dir[i] = d;
00184       return d;
00185     }
00186 
00187     bool sat() const {
00188       DebugAssert(!isNull(), "Clause::sat()");
00189       return d_clause->d_sat;
00190     }
00191 
00192     bool sat(bool ignored) const {
00193       DebugAssert(!isNull(), "Clause::sat()");
00194       bool flag = false;
00195       if (!d_clause->d_sat) {
00196         for (size_t i = 0; !flag && i < d_clause->d_literals.size(); ++i)
00197           if (d_clause->d_literals[i].getValue() == 1)
00198             flag = true;
00199       }
00200       if (flag) {
00201         
00202         markSat();
00203       }
00204       return d_clause->d_sat;
00205     }
00206     
00207     void markSat() const {
00208       DebugAssert(!isNull(), "Clause::markSat()");
00209       d_clause->d_sat = true;
00210     }
00211     
00212     bool deleted() const {
00213       DebugAssert(!isNull(), "Clause::deleted()");
00214       return d_clause->d_deleted;
00215     }
00216     void markDeleted() const;
00217 
00218     
00219     size_t id() const { return (size_t) d_clause; }
00220 
00221     
00222     bool operator==(const Clause& c) const { return d_clause == c.d_clause; }
00223 
00224 
00225     int owners() const { return d_clause->d_refcountOwner; }
00226     
00227     
00228     std::string toString() const;
00229 
00230     friend std::ostream& operator<<(std::ostream& os, const Clause& c);
00231 
00232     IF_DEBUG(bool wpCheck() const;)
00233     IF_DEBUG(const std::string& getFile() const { return d_clause->d_file; })
00234     IF_DEBUG(int getLine() const { return d_clause->d_line; })
00235 
00236   }; 
00237 
00238 
00239 
00240 
00241 
00242   class ClauseOwner {
00243     Clause d_clause;
00244 
00245     ClauseOwner() { }
00246   public:
00247 
00248     ClauseOwner(const Clause& c): d_clause(c) { d_clause.countOwner()++; }
00249 
00250     ClauseOwner(TheoryCore* core, VariableManager* vm, const Theorem& clause,
00251     int scope): d_clause(core, vm, clause, scope) {
00252       d_clause.countOwner()++;
00253     }
00254 
00255     ClauseOwner(const ClauseOwner& c): d_clause(c.d_clause) {
00256       d_clause.countOwner()++;
00257     }
00258 
00259     ClauseOwner& operator=(const ClauseOwner& c) {
00260       if(&c == this) return *this; 
00261       DebugAssert(d_clause.countOwner() > 0, "in operator=");
00262       if(--(d_clause.countOwner()) == 0)
00263   d_clause.markDeleted();
00264       d_clause = c.d_clause;
00265       d_clause.countOwner()++;
00266       return *this;
00267     }
00268 
00269     ~ClauseOwner() {
00270       FatalAssert(d_clause.countOwner() > 0, "in ~ClauseOwner");
00271       if(--(d_clause.countOwner()) == 0) {
00272   d_clause.markDeleted();
00273       }
00274     }
00275 
00276     operator Clause& () { return d_clause; }
00277 
00278     operator const Clause& () const { return d_clause; }
00279   }; 
00280     
00281 
00282   
00283 
00284   
00285   
00286   class CompactClause {
00287   private:
00288     Clause d_clause;
00289   public:
00290     CompactClause(const Clause& c): d_clause(c) { }
00291     friend std::ostream& operator<<(std::ostream& os, const CompactClause& c);
00292     std::string toString() const;
00293   };
00294 
00295 } 
00296     
00297 #endif