Skip to content
Snippets Groups Projects
Commit 5099743b authored by Jonathan Lambrechts's avatar Jonathan Lambrechts
Browse files

work on dg functions

parent 0b3bfed5
Branches
Tags
No related merge requests found
...@@ -37,6 +37,7 @@ extern "C" { ...@@ -37,6 +37,7 @@ extern "C" {
std::complex<double> *alpha, std::complex<double> *a, int *lda, std::complex<double> *alpha, std::complex<double> *a, int *lda,
std::complex<double> *x, int *incx, std::complex<double> *beta, std::complex<double> *x, int *incx, std::complex<double> *beta,
std::complex<double> *y, int *incy); std::complex<double> *y, int *incy);
void F77NAME(dscal)(int *n, double *alpha,double *x, int *incx);
} }
template<> template<>
...@@ -46,6 +47,18 @@ void fullVector<double>::axpy(fullVector<double> &x,double alpha) ...@@ -46,6 +47,18 @@ void fullVector<double>::axpy(fullVector<double> &x,double alpha)
F77NAME(daxpy)(&M, &alpha, x._data,&INCX, _data, &INCY); F77NAME(daxpy)(&M, &alpha, x._data,&INCX, _data, &INCY);
} }
template<>
void fullMatrix<double>::scale(const double s) {
int N = _r*_c;
int stride = 1;
double ss = s;
F77NAME(dscal)(&N, &ss,_data, &stride);
/*if(s == 0.)
for(int i = 0; i < _r * _c; ++i) _data[i] = 0.;
else
for(int i = 0; i < _r * _c; ++i) _data[i] *= s;*/
}
template<> template<>
void fullMatrix<double>::mult(const fullMatrix<double> &b, fullMatrix<double> &c) const void fullMatrix<double>::mult(const fullMatrix<double> &b, fullMatrix<double> &c) const
{ {
......
...@@ -144,7 +144,7 @@ class fullMatrix ...@@ -144,7 +144,7 @@ class fullMatrix
} }
fullMatrix() : _own_data(false),_r(0), _c(0), _data(0) {} fullMatrix() : _own_data(false),_r(0), _c(0), _data(0) {}
~fullMatrix() { if(_data && _own_data) delete [] _data; } ~fullMatrix() { if(_data && _own_data) delete [] _data; }
bool resize(int r, int c) // data will be owned (same as constructor) bool resize(int r, int c, bool resetValue = true) // data will be owned (same as constructor)
{ {
if ((r * c > _r * _c) || !_own_data){ if ((r * c > _r * _c) || !_own_data){
_r = r; _r = r;
...@@ -152,6 +152,7 @@ class fullMatrix ...@@ -152,6 +152,7 @@ class fullMatrix
if (_own_data && _data) delete[] _data; if (_own_data && _data) delete[] _data;
_data = new scalar[_r * _c]; _data = new scalar[_r * _c];
_own_data = true; _own_data = true;
if(resetValue)
scale(0.); scale(0.);
return true; return true;
} }
...@@ -159,6 +160,7 @@ class fullMatrix ...@@ -159,6 +160,7 @@ class fullMatrix
_r = r; _r = r;
_c = c; _c = c;
} }
if(resetValue)
scale(0.); scale(0.);
return false; // no reallocation return false; // no reallocation
} }
...@@ -272,13 +274,17 @@ class fullMatrix ...@@ -272,13 +274,17 @@ class fullMatrix
{ {
for(int i = 0; i < _r * _c; i++) _data[i] = m._data[i]; for(int i = 0; i < _r * _c; i++) _data[i] = m._data[i];
} }
inline void scale(const double s) void scale(const double s)
#if !defined(HAVE_BLAS)
{ {
if(s == 0.) if(s == 0.)
for(int i = 0; i < _r * _c; ++i) _data[i] = 0.; for(int i = 0; i < _r * _c; ++i) _data[i] = 0.;
else else
for(int i = 0; i < _r * _c; ++i) _data[i] *= s; for(int i = 0; i < _r * _c; ++i) _data[i] *= s;
} }
#endif
;
inline void add(const double &a) inline void add(const double &a)
{ {
for(int i = 0; i < _r * _c; ++i) _data[i] += a; for(int i = 0; i < _r * _c; ++i) _data[i] += a;
......
...@@ -9,112 +9,128 @@ ...@@ -9,112 +9,128 @@
#include "dlfcn.h" #include "dlfcn.h"
#endif #endif
#include "Bindings.h" #include "Bindings.h"
struct functionReplaceCache {
dataCacheMap *map;
std::vector <dataCacheDouble*> toReplace;
std::vector <dataCacheDouble*> toCompute;
};
function::~function() { function::~function() {
} }
function::function(int nbCol, bool invalidatedOnElement):_nbCol(nbCol), _invalidatedOnElement(invalidatedOnElement){} function::function(int nbCol, bool invalidatedOnElement):_nbCol(nbCol), _invalidatedOnElement(invalidatedOnElement){}
void function::addFunctionReplace(functionReplace &fr) { void function::addFunctionReplace(functionReplace &fr) {
fr._master = this;
_functionReplaces.push_back(&fr); _functionReplaces.push_back(&fr);
} }
dataCacheDouble::~dataCacheDouble() void function::setArgument(fullMatrix<double> &v, const function *f, int iMap) {
{ if(f==NULL)
for(unsigned i = 0; i< functionReplaceCaches.size(); i++) { throw;
delete functionReplaceCaches[i]; arguments.push_back(argument(v, iMap, f));
dependencies.insert(dependency(iMap, f));
for(std::set<dependency>::iterator it = f->dependencies.begin(); it != f->dependencies.end(); it++) {
if (it->iMap> 0 && iMap >0)
Msg::Error("consecutive secondary caches");
dependencies.insert(dependency(iMap + it->iMap, it->f));
} }
}; for (int i = 0; i < _functionReplaces.size(); i++) {
functionReplace &replace = *_functionReplaces[i];
void dataCacheDouble::addMeAsDependencyOf (dataCacheDouble *newDep) for (std::set<dependency>::iterator it = replace._fromParent.begin(); it != replace._fromParent.end(); it++) {
{ if (it->iMap> 0 && iMap >0)
_dependOnMe.insert(newDep); Msg::Error("consecutive secondary caches");
newDep->_iDependOn.insert(this); dependencies.insert(dependency(iMap + it->iMap, it->f));
for(std::set<dataCacheDouble*>::iterator it = _iDependOn.begin();
it != _iDependOn.end(); it++) {
(*it)->_dependOnMe.insert(newDep);
newDep->_iDependOn.insert(*it);
} }
} }
dataCacheDouble::dataCacheDouble(dataCacheMap &m, int nRowByPoint, int nbCol):
_cacheMap(m),_value(m.getNbEvaluationPoints()*nRowByPoint,nbCol)
{
_nRowByPoint=nRowByPoint;
m.addDataCacheDouble(this,true);
_function = NULL;
} }
dataCacheDouble::dataCacheDouble(dataCacheMap *m, function *f): dataCacheDouble::dataCacheDouble(dataCacheMap *m, function *f):
_cacheMap(*m),_value(m->getNbEvaluationPoints(),f->getNbCol()) _cacheMap(*m),_value(m->getNbEvaluationPoints(),f->getNbCol()), _function(f)
{ {
_nRowByPoint=1;
m->addDataCacheDouble(this, f->isInvalitedOnElement()); m->addDataCacheDouble(this, f->isInvalitedOnElement());
_function = f;
for(unsigned i=0; i<f->_childrenCache.size(); i++) {
m->addSecondaryCache(m->newChild()); }
_substitutions.resize(f->_substitutedFunctions.size());
for(unsigned i=0; i<f->_substitutedFunctions.size(); i++) {
function::substitutedFunction s = f->_substitutedFunctions[i];
_substitutions[i].first = &m->getSecondaryCache(s.iMap)->substitute(s.f0);
_substitutions[i].second = &m->get(s.f1,this);
}
_dependencies.resize ( _function->arguments.size());
for (unsigned int i=0;i<_function->arguments.size();i++) {
int iCache = _function->arguments[i].iMap;
const function *f = _function->arguments[i].f;
_dependencies[i] = &m->getSecondaryCache(iCache)->get(f,this);
}
for (unsigned i = 0; i < f->_functionReplaces.size(); i++) {
functionReplaceCaches.push_back (new functionReplaceCache(m, f->_functionReplaces[i], this));
}
f->registerInDataCacheMap(m, this);
} }
void dataCacheDouble::resize() { void dataCacheDouble::resize(int nrow) {
_value = fullMatrix<double>(_nRowByPoint==0?1:_nRowByPoint*_cacheMap.getNbEvaluationPoints(),_value.size2()); _value.resize(nrow, _value.size2());
_valid = false;
} }
void dataCacheDouble::_eval() { void dataCacheDouble::_eval() {
for(unsigned int i=0;i<_dependencies.size(); i++){ for(unsigned int i=0;i<_directDependencies.size(); i++){
_function->arguments[i].val->setAsProxy((*_dependencies[i])()); _function->arguments[i].val->setAsProxy(_directDependencies[i]->get());
} }
for (unsigned i = 0; i < _function->_functionReplaces.size(); i++) { for (unsigned i = 0; i < _function->_functionReplaces.size(); i++) {
_function->_functionReplaces[i]->currentCache = functionReplaceCaches[i]; _function->_functionReplaces[i]->currentCache = &functionReplaceCaches[i];
for (unsigned j = 0; j < functionReplaceCaches[i]->toReplace.size() ; j++){ for (unsigned j = 0; j < functionReplaceCaches[i].toReplace.size() ; j++){
_function->_functionReplaces[i]->_toReplace[j].val->setAsProxy((*functionReplaceCaches[i]->toReplace[j])._value); _function->_functionReplaces[i]->_toReplace[j].val->setAsProxy((*functionReplaceCaches[i].toReplace[j])._value);
} }
} }
_function->call(&_cacheMap, _value); _function->call(&_cacheMap, _value);
_valid = true;
} }
//dataCacheMap members
dataCacheDouble &dataCacheMap::get(const function *f, dataCacheDouble *caller) { dataCacheDouble &dataCacheMap::get(const function *f, dataCacheDouble *caller) {
// do I have a cache for this function ?
dataCacheDouble *&r = _cacheDoubleMap[f]; dataCacheDouble *&r = _cacheDoubleMap[f];
dataCacheMap *cParent = _parent; // can I use the cache of my parent ?
while (cParent && r==NULL) { if(_parent && r==NULL) {
/*std::map<const function *, dataCacheDouble *>::iterator it = cParent->_cacheDoubleMap.find(f); bool okFromParent = true;
if (it != cParent->_cacheDoubleMap.end()) {*/ for (std::set<function::dependency>::iterator it = f->dependencies.begin(); it != f->dependencies.end(); it++) {
// r = it->second; if (it->iMap > _parent->_secondaryCaches.size())
r = &_parent->get(f,caller); okFromParent=false;
for (std::set<dataCacheDouble*>::iterator dep = r->_iDependOn.begin(); dep != r->_iDependOn.end(); dep++) { dataCacheMap *m = getSecondaryCache(it->iMap);
//if (_cacheDoubleMap.find((*dep)->_function) != _cacheDoubleMap.end()) { if (m->_cacheDoubleMap.find(it->f) != m->_cacheDoubleMap.end()) {
if (&get((*dep)->_function) != *dep) { okFromParent = false;
r = NULL;
break; break;
} }
} }
//} if (okFromParent)
cParent = cParent->_parent; r = &_parent->get (f,caller);
} }
if (r==NULL) // no cache found, create a new one
if (r==NULL) {
r = new dataCacheDouble (this, (function*)(f)); r = new dataCacheDouble (this, (function*)(f));
if (caller) r->_directDependencies.resize (f->arguments.size());
r->addMeAsDependencyOf(caller); for (unsigned int i = 0; i < f->arguments.size(); i++) {
return *r; r->_directDependencies[i] = &getSecondaryCache(f->arguments[i].iMap)->get (f->arguments[i].f, r);
}
for (unsigned i = 0; i < f->_functionReplaces.size(); i++) {
functionReplaceCache replaceCache;
functionReplace *replace = f->_functionReplaces[i];
dataCacheMap *rMap = newChild();
for (unsigned i = 0; i < _secondaryCaches.size(); i ++)
rMap->addSecondaryCache (getSecondaryCache(i+1)->newChild());
for (int i = 0; i < replace->_nChildren; i ++)
rMap->addSecondaryCache (rMap->newChild());
for (std::vector<function::argument>::iterator it = replace->_toReplace.begin(); it!= replace->_toReplace.end(); it++ ) {
dataCacheMap *m = rMap->getSecondaryCache(it->iMap);
dataCacheDouble *s = new dataCacheDouble(m, (function*)it->f);
m->_cacheDoubleMap[it->f] = s;
replaceCache.toReplace.push_back(s);
}
for (std::vector<function::argument>::iterator it = replace->_toCompute.begin(); it!= replace->_toCompute.end(); it++ ) {
replaceCache.toCompute.push_back (&rMap->getSecondaryCache(it->iMap)->get(it->f, r));
}
replaceCache.map = rMap;
r->functionReplaceCaches.push_back (replaceCache);
}
((function*)f)->registerInDataCacheMap(this, r);
} }
dataCacheDouble &dataCacheMap::substitute(const function *f) // update the dependency tree
{ if (caller) {
dataCacheDouble *&r= _cacheDoubleMap[f]; r->_dependOnMe.insert(caller);
r = new dataCacheDouble(this, (function*)(f)); caller->_iDependOn.insert(r);
for(std::set<dataCacheDouble*>::iterator it = r->_iDependOn.begin(); it != r->_iDependOn.end(); it++) {
(*it)->_dependOnMe.insert(caller);
caller->_iDependOn.insert(*it);
}
}
return *r; return *r;
} }
...@@ -124,8 +140,50 @@ dataCacheMap::~dataCacheMap() ...@@ -124,8 +140,50 @@ dataCacheMap::~dataCacheMap()
it!=_allDataCaches.end(); it++) { it!=_allDataCaches.end(); it++) {
delete *it; delete *it;
} }
for (std::list<dataCacheMap*>::iterator it = _children.begin(); it != _children.end(); it++) {
delete *it;
}
} }
void functionReplace::replace(fullMatrix<double> &v, const function *f, int iMap) {
_replaced.insert(function::dependency(iMap,f));
_toReplace.push_back(function::argument(v, iMap, f));
}
void functionReplace::get(fullMatrix<double> &v, const function *f, int iMap) {
bool allDepFromParent = true;
for (std::set<function::dependency>::iterator itDep = f->dependencies.begin(); itDep != f->dependencies.end(); itDep++){
bool depFromParent = (_replaced.count(*itDep)==0);
for (std::set<function::dependency>::iterator itDep2 = itDep->f->dependencies.begin(); itDep2 != itDep->f->dependencies.end() && depFromParent; itDep2++)
depFromParent &= (_replaced.count(*itDep2)==0);
if(depFromParent)
_master->dependencies.insert(*itDep);
else
allDepFromParent = false;
}
function::dependency asDep(iMap, f);
if (allDepFromParent && _replaced.count(asDep)==0)
_master->dependencies.insert(asDep);
_toCompute.push_back(function::argument(v, iMap, f));
}
void functionReplace::addChild() {
_nChildren++;
}
functionReplace::functionReplace(){
_nChildren=0;
}
void functionReplace::compute(){
for (unsigned i = 0; i < _toReplace.size(); i++){
currentCache->toReplace[i]->set();
}
for (unsigned i = 0; i < _toCompute.size(); i++) {
_toCompute[i].val->setAsProxy(currentCache->toCompute[i]->get());
}
};
// now some example of functions // now some example of functions
// constant values copied over each line // constant values copied over each line
...@@ -407,8 +465,7 @@ class functionLua : public function { ...@@ -407,8 +465,7 @@ class functionLua : public function {
void dataCacheMap::setNbEvaluationPoints(int nbEvaluationPoints) { void dataCacheMap::setNbEvaluationPoints(int nbEvaluationPoints) {
_nbEvaluationPoints = nbEvaluationPoints; _nbEvaluationPoints = nbEvaluationPoints;
for(std::set<dataCacheDouble*>::iterator it = _allDataCaches.begin(); it!= _allDataCaches.end(); it++){ for(std::set<dataCacheDouble*>::iterator it = _allDataCaches.begin(); it!= _allDataCaches.end(); it++){
(*it)->resize(); (*it)->resize(nbEvaluationPoints);
(*it)->_valid = false;
} }
for(std::list<dataCacheMap*>::iterator it = _children.begin(); it!= _children.end(); it++) { for(std::list<dataCacheMap*>::iterator it = _children.begin(); it!= _children.end(); it++) {
(*it)->setNbEvaluationPoints(nbEvaluationPoints); (*it)->setNbEvaluationPoints(nbEvaluationPoints);
...@@ -562,44 +619,6 @@ void function::registerBindings(binding *b){ ...@@ -562,44 +619,6 @@ void function::registerBindings(binding *b){
#endif #endif
} }
void functionReplace::replace(fullMatrix<double> &v, const function *f, int iMap) {
_toReplace.push_back(function::argument(v, iMap, f));
}
void functionReplace::get(fullMatrix<double> &v, const function *f, int iMap) {
_toCompute.push_back(function::argument(v, iMap, f));
}
void functionReplace::compute(){
for (unsigned i = 0; i < _toReplace.size(); i++){
currentCache->toReplace[i]->set();
}
for (unsigned i = 0; i < _toCompute.size(); i++) {
currentCache->toCompute[i]->_valid =false;
_toCompute[i].val->setAsProxy((*currentCache->toCompute[i])());
}
};
functionReplaceCache::functionReplaceCache(dataCacheMap *m, functionReplace *rep, dataCacheDouble *from) {
map = m->newChild();
for (unsigned i = 0; i < m->_secondaryCaches.size(); i ++) {
map->addSecondaryCache (m->getSecondaryCache(i+1)->newChild());
}
for (unsigned i = 0; i < rep->_toReplace.size(); i++) {
toReplace.push_back (&map->getSecondaryCache(rep->_toReplace[i].iMap)->substitute(rep->_toReplace[i].f));
}
for (unsigned i = 0; i < rep->_toCompute.size(); i++) {
dataCacheMap *m2 = map->getSecondaryCache(rep->_toCompute[i].iMap);
toCompute.push_back (&m2->get(rep->_toCompute[i].f, from));
}
}
functionReplaceCache::~functionReplaceCache() {
for (unsigned i = 0; i< map->_secondaryCaches.size(); i++) {
delete map->_secondaryCaches[i];
}
delete map;
}
functionConstant *function::_timeFunction = NULL; functionConstant *function::_timeFunction = NULL;
functionConstant *function::getTime() { functionConstant *function::getTime() {
if (! _timeFunction) if (! _timeFunction)
......
...@@ -21,56 +21,46 @@ class functionReplaceCache; ...@@ -21,56 +21,46 @@ class functionReplaceCache;
// An abstract interface to functions // An abstract interface to functions
// more explanation at the head of this file // more explanation at the head of this file
class function { class function {
static functionConstant *_timeFunction;
static functionConstant *_dtFunction;
public :
class argument {
//iMap is the id of the dataCacheMap, e.g. on interfaces
public : public :
int iMap; int _nbCol;
const function *f; bool _invalidatedOnElement;
fullMatrix<double> *val; std::vector<functionReplace*> _functionReplaces;
argument(fullMatrix<double> &v, int iMap_, const function *f_){ class dependency {
val = &v; public : int iMap; const function *f;
iMap = iMap_; dependency(int iMap_, const function *f_){iMap = iMap_; f = f_; }
f = f_; bool operator < (const dependency &d) const {
return (d.iMap <iMap || d.f < f);
} }
}; };
std::vector<functionReplace*> _functionReplaces; void printDep() {
class substitutedFunction { for(std::set<dependency>::iterator it = dependencies.begin(); it != dependencies.end(); it++)
printf("%i %p\n", it->iMap, it->f);
}
class argument {
//iMap is the id of the dataCacheMap, e.g. on interfaces
public: public:
int iMap; int iMap; const function *f; fullMatrix<double> *val;
const function *f0, *f1; // f1 replaces f0 argument(fullMatrix<double> &v, int iMap_, const function *f_){ val = &v; iMap = iMap_; f = f_; }
}; };
int _nbCol;
bool _invalidatedOnElement;
std::vector<int> _childrenCache;
std::vector<substitutedFunction> _substitutedFunctions;
virtual void call (dataCacheMap *m, fullMatrix<double> &res)=0;
virtual void registerInDataCacheMap(dataCacheMap *m, dataCacheDouble *d) {}
std::vector<argument> arguments; std::vector<argument> arguments;
const void setArgument(fullMatrix<double> &v, const function *f, int iMap = 0) { std::set<dependency> dependencies;
if(f==NULL) void setArgument(fullMatrix<double> &v, const function *f, int iMap = 0);
throw; void addFunctionReplace(functionReplace &fr);
arguments.push_back(argument(v, iMap, f));
}
void addChildDataCacheMap(int parent) {
_childrenCache.push_back(parent);
}
void substituteFunction( int iMap, const function *f0, const function *f1) {
substitutedFunction s;
s.iMap= iMap;
s.f0 = f0;
s.f1 = f1;
_substitutedFunctions.push_back(s);
}
virtual ~function();
static void registerBindings(binding *b);
function(int nbCol, bool invalidatedOnElement = true); function(int nbCol, bool invalidatedOnElement = true);
inline int getNbCol()const {return _nbCol;} virtual ~function();
virtual void call (dataCacheMap *m, fullMatrix<double> &res)=0;
virtual void registerInDataCacheMap(dataCacheMap *m, dataCacheDouble *d) {}
inline bool isInvalitedOnElement() { return _invalidatedOnElement;} inline bool isInvalitedOnElement() { return _invalidatedOnElement;}
void addFunctionReplace(functionReplace &fr); inline int getNbCol()const {return _nbCol;}
static void registerBindings(binding *b);
private:
static functionConstant *_timeFunction;
static functionConstant *_dtFunction;
public:
static function *getSolution(); static function *getSolution();
static function *getSolutionGradient(); static function *getSolutionGradient();
static function *getParametricCoordinates(); static function *getParametricCoordinates();
...@@ -84,41 +74,24 @@ class function { ...@@ -84,41 +74,24 @@ class function {
// then the size of the matrix is automatically adjusted // then the size of the matrix is automatically adjusted
class dataCacheDouble { class dataCacheDouble {
friend class dataCacheMap; friend class dataCacheMap;
public: friend class dgDataCacheMap;
friend class functionReplace;
std::vector<dataCacheDouble*> _directDependencies;
function *_function;
dataCacheMap &_cacheMap;
std::vector<functionReplaceCache> functionReplaceCaches;
protected:
// pointers to all of the dataCache depending on me // pointers to all of the dataCache depending on me
std::set<dataCacheDouble*> _dependOnMe; std::set<dataCacheDouble*> _dependOnMe;
std::set<dataCacheDouble*> _iDependOn; std::set<dataCacheDouble*> _iDependOn;
protected : fullMatrix<double> _value;
// invalidates all the cached data that depends on me
inline void _invalidateDependencies()
{
// if this is too slow we can keep a C array cache of the _dependOnMe set
for(std::set<dataCacheDouble*>::iterator it = _dependOnMe.begin();
it!=_dependOnMe.end(); it++)
(*it)->_valid=false;
}
public :
bool _valid; bool _valid;
// dataCacheMap is the only one supposed to call this dataCacheDouble(dataCacheMap *,function *f);
void addMeAsDependencyOf (dataCacheDouble *newDep);
inline bool somethingDependOnMe() {
return !_dependOnMe.empty();
}
inline bool doIDependOn(dataCacheDouble &other) {
return (_iDependOn.find(&other)!=_iDependOn.end());
}
std::vector<dataCacheDouble*> _dependencies;
std::vector<std::pair<dataCacheDouble*, dataCacheDouble*> > _substitutions;
int _nRowByPoint;
function *_function;
dataCacheMap &_cacheMap;
// do the actual computation and put the result into _value // do the actual computation and put the result into _value
// still virtual because it is overrided by conservation law terms, as soon as conservation law terms will be regular functions, we will remove this void _eval();
virtual void _eval(); void resize(int nrow);
public: public:
fullMatrix<double> _value;
//set the value (without computing it by _eval) and invalidate the dependencies //set the value (without computing it by _eval) and invalidate the dependencies
// this function is needed to be able to pass the _value to functions like gemm or mult // this function is needed to be able to pass the _value to functions like gemm or mult
// but you cannot keep the reference to the _value, you should always use the set function // but you cannot keep the reference to the _value, you should always use the set function
...@@ -126,41 +99,33 @@ public : ...@@ -126,41 +99,33 @@ public :
// take care if you use this to set a proxy you must ensure that the value pointed to are not modified // take care if you use this to set a proxy you must ensure that the value pointed to are not modified
// without further call to set because the dependencies won't be invalidate // without further call to set because the dependencies won't be invalidate
inline fullMatrix<double> &set() { inline fullMatrix<double> &set() {
if(_valid) if(_valid) {
_invalidateDependencies(); for(std::set<dataCacheDouble*>::iterator it = _dependOnMe.begin();
_valid = true; it!=_dependOnMe.end(); it++)
return _value; (*it)->_valid=false;
} }
std::vector<functionReplaceCache*> functionReplaceCaches;
inline const double &operator () (int i, int j)
{
if(!_valid) {
_eval();
_valid = true; _valid = true;
} return _value;
return _value(i,j);
} }
//access _value and compute it if necessary //access _value and compute it if necessary
inline const fullMatrix<double> &operator () () inline const fullMatrix<double> &get() {
{ if(!_valid)
if(!_valid) {
_eval(); _eval();
_valid=true;
}
return _value; return _value;
} }
void resize(); // dataCacheMap is the only one supposed to call this
dataCacheDouble(dataCacheMap *,function *f); inline bool somethingDependOnMe() {
dataCacheDouble(dataCacheMap &m, int nRowByPoint, int nbCol); return !_dependOnMe.empty();
virtual ~dataCacheDouble(); }
inline bool doIDependOn(dataCacheDouble &other) {
return (_iDependOn.find(&other)!=_iDependOn.end());
}
}; };
class dgDataCacheMap; class dgDataCacheMap;
// more explanation at the head of this file // more explanation at the head of this file
class dataCacheMap { class dataCacheMap {
friend class dataCacheDouble;
public: public:
dataCacheMap *_parent; dataCacheMap *_parent;
std::list<dataCacheMap*> _children; std::list<dataCacheMap*> _children;
...@@ -177,10 +142,6 @@ class dataCacheMap { ...@@ -177,10 +142,6 @@ class dataCacheMap {
if(invalidatedOnElement) if(invalidatedOnElement)
_toInvalidateOnElement.insert(data); _toInvalidateOnElement.insert(data);
} }
void printList() {
for(std::set<dataCacheDouble*>::iterator it = _toInvalidateOnElement.begin(); it!= _toInvalidateOnElement.end(); it++)
printf("%p\n",*it);
}
virtual dgDataCacheMap *asDgDataCacheMap() { virtual dgDataCacheMap *asDgDataCacheMap() {
Msg::Error("I'm not a dgDataCacheMap\n"); Msg::Error("I'm not a dgDataCacheMap\n");
return NULL; return NULL;
...@@ -194,7 +155,6 @@ class dataCacheMap { ...@@ -194,7 +155,6 @@ class dataCacheMap {
_secondaryCaches.push_back(s); _secondaryCaches.push_back(s);
} }
dataCacheDouble &get(const function *f, dataCacheDouble *caller=0); dataCacheDouble &get(const function *f, dataCacheDouble *caller=0);
dataCacheDouble &substitute(const function *f);
virtual void setElement(MElement *element) { virtual void setElement(MElement *element) {
_element=element; _element=element;
for(std::set<dataCacheDouble*>::iterator it = _toInvalidateOnElement.begin(); it!= _toInvalidateOnElement.end(); it++) { for(std::set<dataCacheDouble*>::iterator it = _toInvalidateOnElement.begin(); it!= _toInvalidateOnElement.end(); it++) {
...@@ -221,27 +181,22 @@ class dataCacheMap { ...@@ -221,27 +181,22 @@ class dataCacheMap {
inline int getNbEvaluationPoints(){return _nbEvaluationPoints;} inline int getNbEvaluationPoints(){return _nbEvaluationPoints;}
~dataCacheMap(); ~dataCacheMap();
}; };
class functionReplace { class functionReplace {
friend class functionReplaceCache; friend class dataCacheMap;
friend class dataCacheDouble; friend class dataCacheDouble;
protected: public :
function *_master;
int _nChildren;
functionReplaceCache *currentCache; functionReplaceCache *currentCache;
std::set <function::dependency> _replaced;
std::set <function::dependency> _fromParent;
std::vector <function::argument> _toReplace; std::vector <function::argument> _toReplace;
std::vector <function::argument> _toCompute; std::vector <function::argument> _toCompute;
public :
void get(fullMatrix<double> &v, const function *, int iMap = 0); void get(fullMatrix<double> &v, const function *, int iMap = 0);
void replace(fullMatrix<double> &v, const function *, int iMap = 0); void replace(fullMatrix<double> &v, const function *, int iMap = 0);
void compute (); void compute ();
}; functionReplace();
void addChild();
class functionReplaceCache {
public :
dataCacheMap *map;
std::vector <dataCacheDouble*> toReplace;
std::vector <dataCacheDouble*> toCompute;
functionReplaceCache(dataCacheMap *m, functionReplace *rep, dataCacheDouble *from);
~functionReplaceCache();
}; };
......
...@@ -2,17 +2,18 @@ ...@@ -2,17 +2,18 @@
#include "function.h" #include "function.h"
void functionDerivator::compute() { void functionDerivator::compute() {
_xRef = _x(); _xRef = _x.get();
_fRef = _f(); _fRef = _f.get();
_dfdx = fullMatrix<double>(_f().size1(),_f().size2()*_x().size2()); _dfdx = fullMatrix<double>(_fRef.size1(),_fRef.size2()*_xRef.size2());
for (int j=0;j<_xRef.size2();j++) { for (int j=0;j<_xRef.size2();j++) {
_xDx = _xRef; _xDx = _xRef;
for (int i=0;i<_fRef.size1();i++) for (int i=0;i<_fRef.size1();i++)
_xDx(i,j) += _epsilon; _xDx(i,j) += _epsilon;
_x.set()=_xDx; _x.set()=_xDx;
const fullMatrix<double> &f = _f.get();
for (int i=0; i<_fRef.size1(); i++) for (int i=0; i<_fRef.size1(); i++)
for (int k=0; k<_fRef.size2(); k++) for (int k=0; k<_fRef.size2(); k++)
_dfdx(i, k*_xRef.size2()+j) = (_f(i,k)-_fRef(i,k))/_epsilon; _dfdx(i, k*_xRef.size2()+j) = (f(i,k)-_fRef(i,k))/_epsilon;
} }
_x.set()=_xRef; _x.set()=_xRef;
}; };
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment