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 #include "SundanceEFDEEvaluator.hpp"
00032 #include "SundanceEvalManager.hpp"
00033 #include "PlayaExceptions.hpp"
00034 #include "SundanceSet.hpp"
00035 #include "PlayaTabs.hpp"
00036 #include "SundanceOut.hpp"
00037 
00038 using namespace Sundance;
00039 using namespace Sundance;
00040 
00041 using namespace Sundance;
00042 using namespace Teuchos;
00043 
00044 
00045 EFDEEvaluator::EFDEEvaluator(
00046   const ExplicitFunctionalDerivativeElement* expr, 
00047   const EvalContext& context
00048   )
00049   : UnaryEvaluator<ExplicitFunctionalDerivativeElement>(expr, context),
00050     constValIndexToArgIndexMap_(),
00051     varValIndexToArgIndexMap_()
00052 {
00053 
00054   Tabs tabs;
00055   SUNDANCE_VERB_LOW(tabs << "initializing EFDE evaluator for " 
00056                     << expr->toString());
00057   SUNDANCE_VERB_MEDIUM(tabs << "return sparsity " << std::endl << *(this->sparsity)());
00058 
00059   
00060 
00061 
00062 
00063 
00064   
00065 
00066   int vecResultIndex = 0;
00067   int constResultIndex = 0;
00068 
00069   const Deriv& fd = expr->fd();
00070 
00071   for (int i=0; i<this->sparsity()->numDerivs(); i++)
00072     {
00073       const MultipleDeriv& d = this->sparsity()->deriv(i);
00074       const DerivState& myState = this->sparsity()->state(i);
00075 
00076       if (myState==ConstantDeriv)
00077       {
00078         Tabs tab2;
00079         SUNDANCE_VERB_HIGH(tab2 
00080           << "deriv is constant, will be stored at index "
00081           << constResultIndex << " in the const result array");
00082         addConstantIndex(i, constResultIndex++);
00083       }
00084       else
00085       {
00086         Tabs tab2;
00087         SUNDANCE_VERB_HIGH(tab2 
00088           << "deriv is variable, will be stored at index "
00089           << vecResultIndex << " in the var result array");
00090         addVectorIndex(i, vecResultIndex++);
00091       }
00092       
00093       MultipleDeriv dArg = d;
00094       dArg.put(fd);
00095 
00096       int argIndex = argSparsitySuperset()->getIndex(dArg);
00097 
00098       
00099       TEUCHOS_TEST_FOR_EXCEPTION(argIndex==-1, std::runtime_error,
00100         "Derivative " << dArg << " expected in argument but not found");
00101 
00102       
00103       const DerivState& argState = argSparsitySuperset()->state(argIndex);
00104       TEUCHOS_TEST_FOR_EXCEPTION(argState != myState, std::logic_error, 
00105         "mismatched states");
00106 
00107       if (argState==ConstantDeriv)
00108       {
00109         int constArgIndex = argEval()->constantIndexMap().get(argIndex);
00110         constValIndexToArgIndexMap_.append(constArgIndex);
00111       }
00112       else
00113       {
00114         int vectorArgIndex = argEval()->vectorIndexMap().get(argIndex);
00115         varValIndexToArgIndexMap_.append(vectorArgIndex);
00116       }
00117     }
00118   
00119   SUNDANCE_VERB_HIGH(tabs 
00120     << " constant index map " 
00121     << constValIndexToArgIndexMap_ << std::endl 
00122     << " vector index map " 
00123     << varValIndexToArgIndexMap_
00124     );
00125 }
00126 
00127 
00128 
00129 void EFDEEvaluator::internalEval(const EvalManager& mgr,
00130   Array<double>& constantResults,
00131   Array<RCP<EvalVector> >& vectorResults) const 
00132 {
00133   TimeMonitor timer(efdeEvalTimer());
00134   Tabs tabs(0);
00135 
00136   SUNDANCE_MSG1(mgr.verb(), tabs << "EFDEEvaluator::eval() expr=" 
00137     << expr()->toString());
00138 
00139   SUNDANCE_MSG3(mgr.verb(), tabs << "sparsity = " << std::endl 
00140     << *(this->sparsity)());
00141 
00142   constantResults.resize(constValIndexToArgIndexMap_.size());
00143   vectorResults.resize(varValIndexToArgIndexMap_.size());
00144 
00145   
00146   Array<RCP<EvalVector> > argVectorResults;
00147   Array<double> argConstantResults;
00148 
00149   evalOperand(mgr, argConstantResults, argVectorResults);
00150 
00151 
00152   if (mgr.verb() > 2)
00153     {
00154       Tabs tab1;
00155       Out::os() << tab1 << "EFDE operand results" << std::endl;
00156       mgr.showResults(Out::os(), argSparsitySuperset(), argVectorResults,
00157           argConstantResults);
00158     }
00159 
00160 
00161   for (int i=0; i<constantResults.size(); i++)
00162   {
00163     constantResults[i] = argConstantResults[constValIndexToArgIndexMap_[i]];
00164   }
00165 
00166   
00167   for (int i=0; i<vectorResults.size(); i++)
00168   {
00169     vectorResults[i] = mgr.popVector();
00170     const RCP<EvalVector>& v = argVectorResults[varValIndexToArgIndexMap_[i]];
00171     vectorResults[i]->setTo_V(v.get());
00172   }
00173 
00174   
00175   
00176 
00177   if (mgr.verb() > 2)
00178   {
00179     Tabs tab1;
00180     Out::os() << tab1 << "EFDE results " << std::endl;
00181     mgr.showResults(Out::os(), this->sparsity(), vectorResults,
00182       constantResults);
00183   }
00184 }
00185