decision_engine_caching.cpp

Go to the documentation of this file.
00001 /*****************************************************************************/
00002 /*!
00003  * \file decision_engine_caching.cpp
00004  * \brief Decision Engine
00005  * 
00006  * <hr>
00007  * Copyright (C) 2003 by the Board of Trustees of Leland Stanford
00008  * Junior University and by New York University. 
00009  *
00010  * License to use, copy, modify, sell and/or distribute this software
00011  * and its documentation for any purpose is hereby granted without
00012  * royalty, subject to the terms and conditions defined in the \ref
00013  * LICENSE file provided with this distribution.  In particular:
00014  *
00015  * - The above copyright notice and this permission notice must appear
00016  * in all copies of the software and related documentation.
00017  *
00018  * - THE SOFTWARE IS PROVIDED "AS-IS", WITHOUT ANY WARRANTIES,
00019  * EXPRESSED OR IMPLIED.  USE IT AT YOUR OWN RISK.
00020  * 
00021  * <hr>
00022  * 
00023  */
00024 /*****************************************************************************/
00025 
00026 
00027 #include "decision_engine_caching.h"
00028 #include "theory_core.h"
00029 #include "search.h"
00030 
00031 
00032 using namespace std;
00033 using namespace CVCL;
00034 
00035 #define CACHE_SIZE 20
00036 #define BASE_TRUST_LEVEL 2
00037 #define TURNOVER_RATE 10
00038 
00039 bool DecisionEngineCaching::isBetter(const Expr& e1, const Expr& e2)
00040 {
00041   ExprMap<int>::iterator it1 = d_index.find(e1.getSimpFrom());
00042   ExprMap<int>::iterator it2 = d_index.find(e2.getSimpFrom());
00043 
00044   if (it1 != d_index.end() &&
00045       (d_cache[it1->second].d_trust + BASE_TRUST_LEVEL >= d_height) &&
00046       (it2 == d_index.end() ||
00047        d_cache[it1->second].d_rank < d_cache[it2->second].d_rank ||
00048        d_cache[it2->second].d_trust + BASE_TRUST_LEVEL < d_height))
00049     return true;
00050   else
00051     return false;
00052 }
00053 
00054 
00055 DecisionEngineCaching::DecisionEngineCaching(TheoryCore* core, SearchImplBase* se)
00056   : DecisionEngine(core, se),
00057     d_startLevel(core->getCM()->scopeLevel()),
00058     d_bottomLevel(0),
00059     d_topLevel(0),
00060     d_topLevelLock(false),
00061     d_height(0),
00062     d_cache(CACHE_SIZE)
00063 {
00064 }
00065 
00066 
00067 Expr DecisionEngineCaching::findSplitter(const Expr& e) {
00068   d_visited.clear();
00069   Expr splitter; // Null by default
00070   if (!e.isNull())
00071   {
00072     d_height = e.getHeight() - 1;
00073     // heights seem to be 1 greater than SVC
00074     // probably because of top-level NOT
00075 
00076     if (!d_topLevelLock)
00077     {
00078       d_topLevel = d_core->getCM()->scopeLevel();
00079       d_topLevelLock = true;
00080     }
00081 
00082     splitter = findSplitterRec(e);
00083     DebugAssert(!splitter.isNull(),
00084                 "findSplitter: can't find splitter in non-literal: "
00085                 + e.toString());
00086     IF_DEBUG(debugger.counter("splitters from non-literals")++);
00087   }
00088   TRACE("splitters verbose", "findSplitter() => ", splitter, "");
00089   return splitter;
00090 }
00091 
00092 
00093 void DecisionEngineCaching::goalSatisfied()
00094 {
00095   if (d_core->getCM()->scopeLevel() - d_bottomLevel != 0)
00096   {
00097     d_bottomLevel = d_core->getCM()->scopeLevel();
00098     return;
00099   }
00100 
00101   if (d_splitters.size() == 0)
00102     return;
00103 
00104   if (!d_topLevelLock)
00105     d_topLevel = d_bottomLevel - 1;
00106   d_topLevelLock = false;
00107 
00108   int numInterestingSplitters = min(d_bottomLevel - d_startLevel - 1, TURNOVER_RATE);
00109   int numSplitters = min(CACHE_SIZE, numInterestingSplitters);
00110 
00111   vector<CacheEntry> newCache(CACHE_SIZE);
00112   ExprMap<int> newIndex;
00113 
00114   int end = d_splitters.size();
00115   int start = end - numSplitters;
00116   if (start < 0)
00117     start = 0;
00118 
00119   for (int i = end - 1, j = 0; i >= start; i--, j++)
00120   {
00121     const Expr& s = d_splitters[i];
00122     Expr splitter = s.getSimpFrom();
00123     if(!splitter.isAbsAtomicFormula()) splitter = s;
00124     newCache[j].d_expr = splitter;
00125     newCache[j].d_rank = (numSplitters - j) % numSplitters;
00126     newIndex[splitter] = j;
00127 
00128     ExprMap<int>::iterator it = d_index.find(splitter);
00129     if (it != d_index.end())
00130     {
00131       if (j == 0) // the effective splitter
00132         newCache[j].d_trust = d_cache[it->second].d_trust + 1;
00133       else
00134         newCache[j].d_trust = d_cache[it->second].d_trust;
00135     }
00136   }
00137 
00138   int i = numSplitters;
00139   int rank = numSplitters;
00140   for (int j = 0; i < CACHE_SIZE && !d_cache[j].d_expr.isNull(); j++)
00141   {
00142     if (!newIndex.count(d_cache[j].d_expr))
00143     {
00144       newCache[i] = d_cache[j];
00145       newCache[i].d_rank = rank++;
00146       newIndex[newCache[i].d_expr] = i;
00147       i++;
00148     }
00149   }
00150 
00151   d_cache = newCache;
00152   d_index = newIndex;
00153   d_bestByExpr.clear();
00154 }

Generated on Thu Apr 13 16:57:30 2006 for CVC Lite by  doxygen 1.4.4