diff --git a/diis.h b/diis.h index b908872..e2fb3c5 100644 --- a/diis.h +++ b/diis.h @@ -16,7 +16,7 @@ // actually it can be anything what has operator=(const T&), clear(), dot() , axpy(), norm() and copyonwrite(), and LA_traits::normtype and elementtype // and get() and put() if external storage is requested -template +template class DIIS { int dim; @@ -24,45 +24,48 @@ class DIIS bool incore; int cyclicshift; //circular buffer of last dim vectors typedef typename LA_traits::elementtype Te; - NRSMat bmat; - AuxStorage *st, *errst; - T *stor, *errstor; + typedef typename LA_traits::elementtype Ue; + NRSMat bmat; + AuxStorage *st; + AuxStorage *errst; + T *stor; + U *errstor; public: DIIS() {dim=0; st=NULL; stor=NULL;}; //for array of diis DIIS(const int n, const bool core=1); void setup(const int n, const bool core=1); ~DIIS(); - typename LA_traits::normtype extrapolate(T &vec, const T &errvec); //vec is input/output; returns square residual norm + typename LA_traits::normtype extrapolate(T &vec, const U &errvec); //vec is input/output; returns square residual norm }; -template -DIIS::DIIS(const int n, const bool core) : dim(n), incore(core), bmat(n,n) +template +DIIS::DIIS(const int n, const bool core) : dim(n), incore(core), bmat(n,n) { st=incore?NULL: new AuxStorage; -errst=incore?NULL: new AuxStorage; +errst=incore?NULL: new AuxStorage; stor= incore? new T[dim] : NULL; -errstor= incore? new T[dim] : NULL; -bmat= (Te)0; for(int i=1; i -void DIIS::setup(const int n, const bool core) +template +void DIIS::setup(const int n, const bool core) { dim=n; incore=core; bmat.resize(n); st=incore?NULL: new AuxStorage; -errst=incore?NULL: new AuxStorage; +errst=incore?NULL: new AuxStorage; stor= incore? new T[dim] : NULL; -errstor= incore? new T[dim] : NULL; -bmat= (Te)0; for(int i=1; i -DIIS::~DIIS() +template +DIIS::~DIIS() { if(st) delete st; if(errst) delete errst; @@ -72,8 +75,8 @@ if(errstor) delete[] errstor; -template -typename LA_traits::normtype DIIS::extrapolate(T &vec, const T &errvec) +template +typename LA_traits::normtype DIIS::extrapolate(T &vec, const U &errvec) { if(!dim) laerror("attempt to extrapolate from uninitialized DIIS"); //if dim exceeded, shift @@ -110,18 +113,18 @@ if(incore) bmat(i,aktdim-1)=errvec.dot(errstor[(i+cyclicshift)%dim]); else { - T tmp = vec; tmp.copyonwrite(); //copy dimensions + U tmp = errvec; tmp.copyonwrite(); //copy dimensions for(int i=1; iget(tmp,(i+cyclicshift)%dim); + errst->get(tmp,(i+cyclicshift)%dim); bmat(i,aktdim-1)= errvec.dot(tmp); } } //prepare rhs-solution vector -NRVec rhs(dim); -rhs= (Te)0; rhs[0]= (Te)-1; +NRVec rhs(dim); +rhs= (Ue)0; rhs[0]= (Ue)-1; //solve for coefficients //@@@@@@ implement checking for bad condition number and eliminating old vectors