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
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067 #ifndef SUPERCLAUSE_H_NOV_2007
00068 #define SUPERCLAUSE_H_NOV_2007
00069
00070 #include "util.h"
00071 #include "mrf.h"
00072 #include "array.h"
00073 #include "hashint.h"
00074 #include <ext/hash_set>
00075 #include "variable.h"
00076
00077 using namespace std;
00078 using namespace __gnu_cxx;
00079
00080 class SuperClause
00081 {
00082 public:
00083
00084 SuperClause(Clause * const & clause, Array<Variable *> * const & eqVars,
00085 Array<int> * const & varIdToCanonicalVarId, bool useImplicit,
00086 double outputWt)
00087 {
00088 int parentSuperClauseId = -1;
00089 outputWt_ = outputWt;
00090 init(clause, eqVars, varIdToCanonicalVarId, useImplicit,
00091 parentSuperClauseId);
00092 }
00093
00094 SuperClause(Clause * const & clause, Array<Variable *> * const & eqVars,
00095 Array<int> * const & varIdToCanonicalVarId, bool useImplicit,
00096 int parentSuperClauseId, double outputWt)
00097 {
00098 outputWt_ = outputWt;
00099 init(clause, eqVars, varIdToCanonicalVarId, useImplicit,
00100 parentSuperClauseId);
00101 }
00102
00103 void init(Clause * const & clause, Array<Variable *> * const & eqVars,
00104 Array<int> * const & varIdToCanonicalVarId, bool useImplicit,
00105 int parentSuperClauseId)
00106 {
00107 clause_ = clause;
00108 constantTuples_ = new IntArrayHashArray();
00109 tupleCnts_ = new Array<double>();
00110 implicitTupleFlags_ = new Array<bool>();
00111 eqVars_ = new Array<Variable *>(*eqVars);
00112 varIdToCanonicalVarId_ = new Array<int>(*varIdToCanonicalVarId);
00113 useImplicit_ = useImplicit;
00114 superClauseId_ = superClauseIndex__++;
00115 parentSuperClauseId_ = parentSuperClauseId;
00116 }
00117
00118 ~SuperClause()
00119 {
00120 delete constantTuples_;
00121 delete tupleCnts_;
00122 delete implicitTupleFlags_;
00123 delete eqVars_;
00124 }
00125
00126 SuperClause * createSuperClauseFromTemplate()
00127 {
00128 return new SuperClause(clause_, eqVars_, varIdToCanonicalVarId_,
00129 useImplicit_, superClauseId_, outputWt_);
00130 }
00131
00132 int getSuperClauseId() { return superClauseId_;}
00133
00134 int getParentSuperClauseId() { return parentSuperClauseId_;}
00135
00136 Clause * getClause() { return clause_;}
00137
00138 double getTupleCount(int index) {return (*tupleCnts_)[index];}
00139
00140 int getNumTuples(){ return constantTuples_->size();}
00141
00142 int getTupleIndex(Array<int> * const & constants)
00143 {
00144 return constantTuples_->find(constants);
00145 }
00146
00147 Array<int> * getConstantTuple(int tindex) {return (*constantTuples_)[tindex];}
00148
00149 Array<int> * getVarIdToCanonicalVarId() { return varIdToCanonicalVarId_;}
00150
00151 bool isUseImplicit() { return useImplicit_;}
00152
00153 bool checkIfImplicit(Array<int> * const & constants)
00154 {
00155 bool isImplicit = false;
00156 for (int i = 0; i < constants->size(); i++)
00157 {
00158 if ((*eqVars_)[i] == NULL)
00159 continue;
00160 if ((*eqVars_)[i]->isImplicit((*constants)[i]))
00161 {
00162 isImplicit = true;
00163 break;
00164 }
00165 }
00166 return isImplicit;
00167 }
00168
00169
00170
00171 void incrementTupleCount(Array<int> * const & constants, double cnt)
00172 {
00173 int index = constantTuples_->find(constants);
00174 (*tupleCnts_)[index] += cnt;
00175 }
00176
00177
00178
00179 bool addConstantTuple(Array<int> * const & constants)
00180 {
00181 bool isImplicit;
00182 int index = constantTuples_->find(constants);
00183
00184 if (index < 0)
00185 {
00186 constantTuples_->append(constants);
00187 tupleCnts_->append(0.0);
00188 if (useImplicit_)
00189 isImplicit = checkIfImplicit(constants);
00190 else
00191 isImplicit = false;
00192 implicitTupleFlags_->append(isImplicit);
00193 return true;
00194 }
00195 else
00196 {
00197 return false;
00198 }
00199 }
00200
00201
00202
00203 void addNewConstantsAndIncrementCount(Array<int> * const & constants,
00204 double cnt)
00205 {
00206 bool addedNew = false;
00207 Array<int>* newConstants = new Array<int>(*constants);
00208
00209 addedNew = addConstantTuple(newConstants);
00210 incrementTupleCount(newConstants,cnt);
00211
00212 if (!addedNew)
00213 delete newConstants;
00214 }
00215
00216
00217 Array<int> * getPredicateConstants(int tindex, Predicate *pred)
00218 {
00219 bool isImplicitTuple = useImplicit_ && (*implicitTupleFlags_)[tindex];
00220 Array<Variable*> *pvars = new Array<Variable *>();
00221 Array<int> * pconstants = new Array<int>;
00222 Array<int> * constants = (*constantTuples_)[tindex];
00223 for (int i = 0; i < pred->getNumTerms(); i++)
00224 {
00225 const Term *term = pred->getTerm(i);
00226 int id = term->getId();
00227 assert(id < 0);
00228 pconstants->append((*constants)[-id]);
00229
00230 if (isImplicitTuple)
00231 pvars->append((*eqVars_)[-id]);
00232 }
00233
00234 if (!isImplicitTuple)
00235 {
00236 delete pvars;
00237 return pconstants;
00238 }
00239
00240
00241 constants = NULL;
00242
00243
00244 Array<bool> *seenIds = new Array<bool>(pconstants->size(), false);
00245 IntHashArray *pconstantsForVar = new IntHashArray();
00246 for (int i = 0; i < pconstants->size(); i++)
00247 {
00248 if (!(*pvars)[i]->isImplicit((*pconstants)[i]) || (*seenIds)[i])
00249 continue;
00250 pconstantsForVar->clear();
00251 for (int j = i; j < pconstants->size(); j++)
00252 {
00253 if(!(*pvars)[j]->isImplicit((*pconstants)[j]))
00254 continue;
00255 if((*pvars)[i] != (*pvars)[j])
00256 continue;
00257 pconstantsForVar->append((*pconstants)[j]);
00258 (*seenIds)[j] = true;
00259 }
00260
00261 for (int j = i; j < pconstants->size(); j++)
00262 {
00263 if(!(*pvars)[j]->isImplicit((*pconstants)[j]))
00264 continue;
00265 if((*pvars)[i] != (*pvars)[j])
00266 continue;
00267 int index = pconstantsForVar->find((*pconstants)[j]);
00268 (*pconstants)[j] = (*pvars)[i]->getImplicitConstant(index);
00269 }
00270 }
00271
00272 delete pvars;
00273 delete seenIds;
00274 delete pconstantsForVar;
00275 return pconstants;
00276 }
00277
00278 int getImplicitCount(Array<int> * const & constants,
00279 Array<bool> * const & relevantIds,
00280 Array<bool> * const & predIds)
00281 {
00282 if(!useImplicit_) return 1;
00283 int cnt = 1;
00284 bool print = false;
00285 Array<bool> *seenIds = new Array<bool>(constants->size(),false);
00286 IntHashArray *constantsForVar = new IntHashArray();
00287 IntHashArray *predConstantsForVar = new IntHashArray();
00288 if (print)
00289 {
00290 cout<<"Constants : ";
00291 printArray(*constants,1,cout);
00292 cout<<endl;
00293 }
00294 for (int i = 0; i < constants->size(); i++)
00295 {
00296 if (!(*relevantIds)[i] || (*seenIds)[i])
00297 continue;
00298 constantsForVar->clear();
00299 predConstantsForVar->clear();
00300 for (int j = i; j < constants->size(); j++)
00301 {
00302 if (!(*relevantIds)[j])
00303 continue;
00304 if ((*eqVars_)[i] != (*eqVars_)[j])
00305 continue;
00306
00307
00308 if (predIds && (*predIds)[j])
00309 predConstantsForVar->append((*constants)[j]);
00310 constantsForVar->append((*constants)[j]);
00311 (*seenIds)[j] = true;
00312 }
00313 int numImplicitConstants = (*eqVars_)[i]->getNumImplicitConstants();
00314 int constantsForVarSize = constantsForVar->size();
00315 int predConstantsForVarSize = predConstantsForVar->size();
00316 assert(predConstantsForVarSize <= constantsForVarSize);
00317
00318 if (print)
00319 {
00320 cout<<"numImplicitConstants = "<<numImplicitConstants;
00321 cout<<", constantsForVarSize = "<<constantsForVarSize<<endl;
00322 cout<<", predConstantsForVarSize = "<<predConstantsForVarSize<<endl;
00323 }
00324 cnt = cnt * Util::permute(numImplicitConstants - predConstantsForVarSize,
00325 constantsForVarSize - predConstantsForVarSize);
00326 }
00327
00328 delete seenIds;
00329 delete constantsForVar;
00330 delete predConstantsForVar;
00331
00332 return cnt;
00333 }
00334
00335
00336
00337 int getImplicitCountJoiningWithPred(int tindex, Predicate *pred)
00338 {
00339
00340 bool isImplicitTuple = useImplicit_ && (*implicitTupleFlags_)[tindex];
00341 if (!isImplicitTuple)
00342 return 1;
00343
00344 Array<int> *constants = (*constantTuples_)[tindex];
00345 Array<bool> *relevantIds = new Array<bool>(constants->size(),true);
00346
00347 for (int i = 0; i < constants->size(); i++)
00348 {
00349 int constantId = (*constants)[i];
00350 if (!(*eqVars_)[i] || !((*eqVars_)[i]->isImplicit(constantId)))
00351 {
00352 (*relevantIds)[i] = false;
00353 }
00354 }
00355
00356 Array<bool> *predIds = new Array<bool>(constants->size(), false);
00357
00358
00359 for (int i = 0; i < pred->getNumTerms(); i++)
00360 {
00361 const Term *term = pred->getTerm(i);
00362 int id = term->getId();
00363 assert(id < 0);
00364 (*predIds)[-id] = true;
00365 }
00366
00367 int cnt = getImplicitCount(constants, relevantIds, predIds);
00368 delete relevantIds;
00369 delete predIds;
00370 return cnt;
00371 }
00372
00373
00374
00375 int getNumImplicitTuples(int tindex)
00376 {
00377
00378 bool isImplicitTuple = useImplicit_ && (*implicitTupleFlags_)[tindex];
00379 if (!isImplicitTuple)
00380 return 1;
00381 Array<int> *constants;
00382 constants = (*constantTuples_)[tindex];
00383 Array<bool> *relevantIds = new Array<bool>(constants->size(), true);
00384 for (int i = 0; i < constants->size(); i++)
00385 {
00386 int constantId = (*constants)[i];
00387 if (!(*eqVars_)[i] || !((*eqVars_)[i]->isImplicit(constantId)))
00388 {
00389 (*relevantIds)[i] = false;
00390 }
00391 }
00392 Array<bool> * predIds = NULL;
00393 int cnt = getImplicitCount(constants, relevantIds, predIds);
00394 delete relevantIds;
00395 return cnt;
00396 }
00397
00398 int getNumTuplesIncludingImplicit()
00399 {
00400 int num = 0;
00401 for (int index = 0; index < constantTuples_->size(); index++)
00402 {
00403 num = num + getNumImplicitTuples(index);
00404 }
00405 return num;
00406 }
00407
00408 double getOutputWt()
00409 {
00410 return outputWt_;
00411 }
00412
00413 void addOutputWt(const double& outputWt)
00414 {
00415 outputWt_ += outputWt;
00416 }
00417
00418
00419 ostream& print(ostream& out)
00420 {
00421 int beginIndex = 1;
00422 for (int i = 0; i < constantTuples_->size(); i++)
00423 {
00424 printArray(*((*constantTuples_)[i]), beginIndex, out);
00425 out << endl;
00426 }
00427 return out;
00428 }
00429
00430
00431 void static resetIndex() { superClauseIndex__ = 0;}
00432
00433 private:
00434 Clause* clause_;
00435 double wtScale_;
00436 IntArrayHashArray *constantTuples_;
00437 Array<bool> * implicitTupleFlags_;
00438 Array<double> * tupleCnts_;
00439 Array<Variable *> * eqVars_;
00440 Array<int> * varIdToCanonicalVarId_;
00441 bool useImplicit_;
00442 int superClauseId_;
00443 int parentSuperClauseId_;
00444 double outputWt_;
00445
00446 static int superClauseIndex__;
00447 };
00448
00449
00450 extern void createSuperClauses(
00451 Array<Array<SuperClause*>*>* const & superClausesArr,
00452 Domain * const & domain);
00453
00454 typedef hash_map<Array<int>*, SuperClause*, HashIntArray, EqualIntArray>
00455 IntArrayToSuperClause;
00456
00457 #endif