diff --git a/tests/debug/Test_general_coarse_pvdagm.cc b/tests/debug/Test_general_coarse_pvdagm.cc index b0b9d4d8..27c5807e 100644 --- a/tests/debug/Test_general_coarse_pvdagm.cc +++ b/tests/debug/Test_general_coarse_pvdagm.cc @@ -36,28 +36,6 @@ Author: Peter Boyle using namespace std; using namespace Grid; -template -class HermOpAdaptor : public LinearOperatorBase -{ - LinearOperatorBase & wrapped; -public: - HermOpAdaptor(LinearOperatorBase &wrapme) : wrapped(wrapme) {}; - void OpDiag (const Field &in, Field &out) { assert(0); } - void OpDir (const Field &in, Field &out,int dir,int disp) { assert(0); } - void OpDirAll (const Field &in, std::vector &out){ assert(0); }; - void Op (const Field &in, Field &out){ - wrapped.HermOp(in,out); - } - void AdjOp (const Field &in, Field &out){ - wrapped.HermOp(in,out); - } - void HermOpAndNorm(const Field &in, Field &out,RealD &n1,RealD &n2){ assert(0); } - void HermOp(const Field &in, Field &out){ - wrapped.HermOp(in,out); - } - -}; - template class PVdagMLinearOperator : public LinearOperatorBase { Matrix &_Mat; @@ -69,78 +47,164 @@ public: void OpDir (const Field &in, Field &out,int dir,int disp) { assert(0); } void OpDirAll (const Field &in, std::vector &out){ assert(0); }; void Op (const Field &in, Field &out){ + std::cout << "Op: PVdag M "< +class ShiftedPVdagMLinearOperator : public LinearOperatorBase { + Matrix &_Mat; + Matrix &_PV; + RealD shift; +public: + ShiftedPVdagMLinearOperator(RealD _shift,Matrix &Mat,Matrix &PV): shift(_shift),_Mat(Mat),_PV(PV){}; + + void OpDiag (const Field &in, Field &out) { assert(0); } + void OpDir (const Field &in, Field &out,int dir,int disp) { assert(0); } + void OpDirAll (const Field &in, std::vector &out){ assert(0); }; + void Op (const Field &in, Field &out){ + std::cout << "Op: PVdag M "< class DumbOperator : public LinearOperatorBase { -public: - LatticeComplex scale; - DumbOperator(GridBase *grid) : scale(grid) - { - scale = 0.0; - LatticeComplex scalesft(grid); - LatticeComplex scaletmp(grid); - for(int d=0;d<4;d++){ - Lattice > x(grid); LatticeCoordinate(x,d+1); - LatticeCoordinate(scaletmp,d+1); - scalesft = Cshift(scaletmp,d+1,1); - scale = 100.0*scale + where( mod(x ,2)==(Integer)0, scalesft,scaletmp); - } - std::cout << " scale\n" << scale << std::endl; - } - // Support for coarsening to a multigrid - void OpDiag (const Field &in, Field &out) {}; - void OpDir (const Field &in, Field &out,int dir,int disp){}; - void OpDirAll (const Field &in, std::vector &out) {}; - - void Op (const Field &in, Field &out){ - out = scale * in; - } - void AdjOp (const Field &in, Field &out){ - out = scale * in; + void AdjOp (const Field &in, Field &out){ + std::cout << "AdjOp: Mdag PV "< +class MGPreconditioner : public LinearFunction< Lattice > { +public: + using LinearFunction >::operator(); + typedef Aggregation Aggregates; + typedef typename Aggregation::FineField FineField; + typedef typename Aggregation::CoarseVector CoarseVector; + typedef typename Aggregation::CoarseMatrix CoarseMatrix; + typedef LinearOperatorBase FineOperator; + typedef LinearFunction FineSmoother; + typedef LinearOperatorBase CoarseOperator; + typedef LinearFunction CoarseSolver; + Aggregates & _Aggregates; + FineOperator & _FineOperator; + FineSmoother & _PreSmoother; + FineSmoother & _PostSmoother; + CoarseOperator & _CoarseOperator; + CoarseSolver & _CoarseSolve; + + int level; void Level(int lv) {level = lv; }; + + MGPreconditioner(Aggregates &Agg, + FineOperator &Fine, + FineSmoother &PreSmoother, + FineSmoother &PostSmoother, + CoarseOperator &CoarseOperator_, + CoarseSolver &CoarseSolve_) + : _Aggregates(Agg), + _FineOperator(Fine), + _PreSmoother(PreSmoother), + _PostSmoother(PostSmoother), + _CoarseOperator(CoarseOperator_), + _CoarseSolve(CoarseSolve_), + level(1) { } + + virtual void operator()(const FineField &in, FineField & out) + { + GridBase *CoarseGrid = _Aggregates.CoarseGrid; + // auto CoarseGrid = _CoarseOperator.Grid(); + CoarseVector Csrc(CoarseGrid); + CoarseVector Csol(CoarseGrid); + FineField vec1(in.Grid()); + FineField vec2(in.Grid()); + + std::cout< PVdagM(Ddwf,Dpv); - HermOpAdaptor HOA(PVdagM); + + typedef PVdagMLinearOperator PVdagM_t; + typedef ShiftedPVdagMLinearOperator ShiftedPVdagM_t; + PVdagM_t PVdagM(Ddwf,Dpv); + ShiftedPVdagM_t ShiftedPVdagM(2.0,Ddwf,Dpv); + // Run power method on HOA?? - PowerMethod PM; PM(HOA,src); + // PowerMethod PM; PM(PVdagM,src); // Warning: This routine calls PVdagM.Op, not PVdagM.HermOp typedef Aggregation Subspace; Subspace AggregatesPD(Coarse5d,FGrid,cb); AggregatesPD.CreateSubspaceChebyshev(RNG5, - HOA, + PVdagM, nbasis, - 5000.0, - 0.02, - 100, - 50, - 50, + 4000.0, + 2.0, + 200, + 200, + 200, 0.0); LittleDiracOperator LittleDiracOpPV(geom,FGrid,Coarse5d); @@ -257,6 +323,58 @@ int main (int argc, char ** argv) std::cout< simple; + NonHermitianLinearOperator LinOpCoarse(LittleDiracOpPV); + PrecGeneralisedConjugateResidualNonHermitian L2PGCR(1.0e-8, 100, LinOpCoarse,simple,10,10); + L2PGCR.Level(2); + c_res=Zero(); + L2PGCR(c_src,c_res); + + //////////////////////////////////////// + // Fine grid smoother + //////////////////////////////////////// + std::cout< simple_fine; + // NonHermitianLinearOperator LinOpSmooth(PVdagM); + PrecGeneralisedConjugateResidualNonHermitian SmootherGCR(0.01,10,ShiftedPVdagM,simple_fine,4,4); + + LatticeFermionD f_src(FGrid); + LatticeFermionD f_res(FGrid); + + f_src = one; // 1 in every element for vector 1. + f_res=Zero(); + SmootherGCR(f_src,f_res); + + typedef MGPreconditioner TwoLevelMG; + + TwoLevelMG TwoLevelPrecon(AggregatesPD, + PVdagM, + SmootherGCR, + SmootherGCR, + LinOpCoarse, + L2PGCR); + + PrecGeneralisedConjugateResidualNonHermitian L1PGCR(1.0e-8,1000,PVdagM,TwoLevelPrecon,8,8); + L1PGCR.Level(1); + + f_res=Zero(); + L1PGCR(f_src,f_res); + std::cout<