Grid 0.7.0
OneFlavourEvenOddRational.h
Go to the documentation of this file.
1/*************************************************************************************
2
3Grid physics library, www.github.com/paboyle/Grid
4
5Source file: ./lib/qcd/action/pseudofermion/OneFlavourEvenOddRational.h
6
7Copyright (C) 2015
8
9Author: Peter Boyle <paboyle@ph.ed.ac.uk>
10
11This program is free software; you can redistribute it and/or modify
12it under the terms of the GNU General Public License as published by
13the Free Software Foundation; either version 2 of the License, or
14(at your option) any later version.
15
16This program is distributed in the hope that it will be useful,
17but WITHOUT ANY WARRANTY; without even the implied warranty of
18MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19GNU General Public License for more details.
20
21You should have received a copy of the GNU General Public License along
22with this program; if not, write to the Free Software Foundation, Inc.,
2351 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
24
25See the full license in the file "LICENSE" in the top level distribution
26directory
27*************************************************************************************/
28 /* END LEGAL */
29#ifndef QCD_PSEUDOFERMION_ONE_FLAVOUR_EVEN_ODD_RATIONAL_H
30#define QCD_PSEUDOFERMION_ONE_FLAVOUR_EVEN_ODD_RATIONAL_H
31
33
35// One flavour rational
37
38// S_f = chi^dag * N(Mpc^dag*Mpc)/D(Mpc^dag*Mpc) * chi
39//
40// Here, M is some operator
41// N and D makeup the rat. poly
42//
43
44template <class Impl>
45class OneFlavourEvenOddRationalPseudoFermionAction : public Action<typename Impl::GaugeField> {
46public:
48
51
56
57private:
58 FermionOperator<Impl> &FermOp; // the basic operator
59
60 // NOT using "Nroots"; IroIro is -- perhaps later, but this wasn't good for us
61 // historically
62 // and hasenbusch works better
63
64 FermionField PhiEven; // the pseudo fermion field for this trajectory
65 FermionField PhiOdd; // the pseudo fermion field for this trajectory
66
67public:
69 Params &p)
70 : FermOp(Op),
71 PhiEven(Op.FermionRedBlackGrid()),
72 PhiOdd(Op.FermionRedBlackGrid()),
73 param(p) {
74 AlgRemez remez(param.lo, param.hi, param.precision);
75
76 // MdagM^(+- 1/2)
77 std::cout << GridLogMessage << "Generating degree " << param.degree
78 << " for x^(1/2)" << std::endl;
79 remez.generateApprox(param.degree, 1, 2);
80 PowerHalf.Init(remez, param.tolerance, false);
81 PowerNegHalf.Init(remez, param.tolerance, true);
82
83 // MdagM^(+- 1/4)
84 std::cout << GridLogMessage << "Generating degree " << param.degree
85 << " for x^(1/4)" << std::endl;
86 remez.generateApprox(param.degree, 1, 4);
87 PowerQuarter.Init(remez, param.tolerance, false);
88 PowerNegQuarter.Init(remez, param.tolerance, true);
89 };
90
91 virtual std::string action_name(){return "OneFlavourEvenOddRationalPseudoFermionAction";}
92
93 virtual std::string LogParameters(){
94 std::stringstream sstream;
95 sstream << GridLogMessage << "["<<action_name()<<"] Low :" << param.lo << std::endl;
96 sstream << GridLogMessage << "["<<action_name()<<"] High :" << param.hi << std::endl;
97 sstream << GridLogMessage << "["<<action_name()<<"] Max iterations :" << param.MaxIter << std::endl;
98 sstream << GridLogMessage << "["<<action_name()<<"] Tolerance :" << param.tolerance << std::endl;
99 sstream << GridLogMessage << "["<<action_name()<<"] Degree :" << param.degree << std::endl;
100 sstream << GridLogMessage << "["<<action_name()<<"] Precision :" << param.precision << std::endl;
101 return sstream.str();
102 }
103
104 virtual void refresh(const GaugeField &U, GridSerialRNG &sRNG, GridParallelRNG &pRNG) {
105 // P(phi) = e^{- phi^dag (MpcdagMpc)^-1/2 phi}
106 // = e^{- phi^dag (MpcdagMpc)^-1/4 (MpcdagMpc)^-1/4 phi}
107 // Phi = MpcdagMpc^{1/4} eta
108 //
109 // P(eta) = e^{- eta^dag eta}
110 //
111 // e^{x^2/2 sig^2} => sig^2 = 0.5.
112 //
113 // So eta should be of width sig = 1/sqrt(2).
114
115 RealD scale = std::sqrt(0.5);
116
117 FermionField eta(FermOp.FermionGrid());
118 FermionField etaOdd(FermOp.FermionRedBlackGrid());
119 FermionField etaEven(FermOp.FermionRedBlackGrid());
120
121 gaussian(pRNG, eta);
122 eta = eta * scale;
123
124 pickCheckerboard(Even, etaEven, eta);
125 pickCheckerboard(Odd, etaOdd, eta);
126
127 FermOp.ImportGauge(U);
128
129 // mutishift CG
132 msCG(Mpc, etaOdd, PhiOdd);
133
135 // FIXME : Clover term not yet..
137
138 assert(FermOp.ConstEE() == 1);
139 PhiEven = Zero();
140 };
141
143 // S = phi^dag (Mdag M)^-1/2 phi
145 virtual RealD S(const GaugeField &U) {
146 FermOp.ImportGauge(U);
147
148 FermionField Y(FermOp.FermionRedBlackGrid());
149
151
154
155 msCG(Mpc, PhiOdd, Y);
156
157 auto grid = FermOp.FermionGrid();
158 auto r=rand();
159 grid->Broadcast(0,r);
160 if ( (r%param.BoundsCheckFreq)==0 ) {
161 FermionField gauss(FermOp.FermionRedBlackGrid());
162 gauss = PhiOdd;
163 HighBoundCheck(Mpc,gauss,param.hi);
164 InverseSqrtBoundsCheck(param.MaxIter,param.tolerance*100,Mpc,gauss,PowerNegHalf);
165 }
166
167 RealD action = norm2(Y);
168 std::cout << GridLogMessage << "Pseudofermion action FIXME -- is -1/4 "
169 "solve or -1/2 solve faster??? "
170 << action << std::endl;
171
172 return action;
173 };
174
176 // Need
177 // dS_f/dU = chi^dag d[N/D] chi
178 //
179 // N/D is expressed as partial fraction expansion:
180 //
181 // a0 + \sum_k ak/(M^dagM + bk)
182 //
183 // d[N/D] is then
184 //
185 // \sum_k -ak [M^dagM+bk]^{-1} [ dM^dag M + M^dag dM ] [M^dag M +
186 // bk]^{-1}
187 //
188 // Need
189 // Mf Phi_k = [MdagM+bk]^{-1} Phi
190 // Mf Phi = \sum_k ak [MdagM+bk]^{-1} Phi
191 //
192 // With these building blocks
193 //
194 // dS/dU = \sum_k -ak Mf Phi_k^dag [ dM^dag M + M^dag dM ] Mf
195 // Phi_k
196 // S = innerprodReal(Phi,Mf Phi);
198 virtual void deriv(const GaugeField &U, GaugeField &dSdU) {
199 const int Npole = PowerNegHalf.poles.size();
200
201 std::vector<FermionField> MPhi_k(Npole, FermOp.FermionRedBlackGrid());
202
203 FermionField X(FermOp.FermionRedBlackGrid());
204 FermionField Y(FermOp.FermionRedBlackGrid());
205
206 GaugeField tmp(FermOp.GaugeGrid());
207
208 FermOp.ImportGauge(U);
209
211
213
214 msCG(Mpc, PhiOdd, MPhi_k);
215
216 dSdU = Zero();
217 for (int k = 0; k < Npole; k++) {
218 RealD ak = PowerNegHalf.residues[k];
219
220 X = MPhi_k[k];
221
222 Mpc.Mpc(X, Y);
223 Mpc.MpcDeriv(tmp, Y, X);
224 dSdU = dSdU + ak * tmp;
225 Mpc.MpcDagDeriv(tmp, X, Y);
226 dSdU = dSdU + ak * tmp;
227 }
228
229 // dSdU = Ta(dSdU);
230 };
231};
232
234
235#endif
void InverseSqrtBoundsCheck(int MaxIter, double tol, LinearOperatorBase< Field > &HermOp, Field &GaussNoise, MultiShiftFunction &PowerNegHalf)
Definition Bounds.h:42
void HighBoundCheck(LinearOperatorBase< Field > &HermOp, Field &Phi, RealD hi)
Definition Bounds.h:6
static const int Even
static const int Odd
RealD norm2(const Lattice< vobj > &arg)
void gaussian(GridParallelRNG &rng, Lattice< vobj > &l)
void pickCheckerboard(int cb, Lattice< vobj > &half, const Lattice< vobj > &full)
GridLogger GridLogMessage(1, "Message", GridLogColours, "NORMAL")
#define NAMESPACE_BEGIN(A)
Definition Namespace.h:35
#define NAMESPACE_END(A)
Definition Namespace.h:36
double RealD
Definition Simd.h:61
static INTERNAL_PRECISION U
Definition Zolotarev.cc:230
Base class for all actions.
Definition ActionBase.h:64
double generateApprox(int num_degree, int den_degree, unsigned long power_num, unsigned long power_den, int a_len, double *a_param, int *a_pow)
Definition Remez.cc:114
virtual RealD S(const GaugeField &U)
Evaluate this action with the given gauge field.
OneFlavourEvenOddRationalPseudoFermionAction(FermionOperator< Impl > &Op, Params &p)
virtual void refresh(const GaugeField &U, GridSerialRNG &sRNG, GridParallelRNG &pRNG)
Refresh pseudofermion fields.
virtual void deriv(const GaugeField &U, GaugeField &dSdU)
virtual std::string action_name()
Report the name of the action.
virtual std::string LogParameters()
Print the parameters of the action.
virtual void Mpc(const Field &in, Field &out)
void MpcDagDeriv(GaugeField &Force, const FermionField &U, const FermionField &V)
void MpcDeriv(GaugeField &Force, const FermionField &U, const FermionField &V)
Definition Simd.h:194