4#include "gauge_field.h"
5#include "dirac/Hasenbusch.h"
6#include "dirac/conjugate_gradient.h"
21template <
typename gauge_field,
typename DIRAC_OP>
24 using vector_type =
typename DIRAC_OP::vector_type;
33 std::vector<Field<vector_type>> old_chi_inv;
35 void setup(
int mre_guess_size) {
43 old_chi_inv[i][
ALL] = 0;
54 setup(mre_guess_size);
68 MRE_guess(psi, chi, D, old_chi_inv);
71 if constexpr (std::is_same<double, typename gauge_field::basetype>::value) {
72 hila::out0 <<
"Starting with single precision inversion\n";
74 auto single_precision = gauge.get_single_precision();
75 typename DIRAC_OP::type_flt D_flt(D, single_precision);
100 inverse.
apply(chi, psi);
101 onsites(D.par) {
action += chi[X].rdot(psi[X]); }
115 inverse.
apply(chi, psi);
117 S[X] += chi[X].rdot(psi[X]);
129 psi[X].gaussian_random();
137 for (
int i = 1; i <
MRE_size; i++) {
138 old_chi_inv[i] = old_chi_inv[i - 1];
140 old_chi_inv[0] = psi;
157 inverse.
apply(chi, psi);
162 D.force(Mpsi, psi, force, 1);
163 D.force(psi, Mpsi, force2, -1);
165 foralldir(dir) { force[dir][
ALL] = -eps * (force[dir][X] + force2[dir][X]); }
181template <
typename gauge_field,
typename DIRAC_OP>
189 : _mh(mh), D_h(d, mh), base_action(D_h, g) {}
191 : _mh(mh), D_h(d, mh), base_action(D_h, g, mre_guess_size) {}
194 : _mh(fa._mh), D_h(fa.D_h), base_action(fa.base_action) {}
206template <
typename gauge_field,
typename DIRAC_OP>
209 using vector_type =
typename DIRAC_OP::vector_type;
220 std::vector<Field<vector_type>> old_chi_inv;
222 void setup(
int mre_guess_size) {
227 MRE_size = mre_guess_size;
228 old_chi_inv.resize(MRE_size);
229 for (
int i = 0; i < MRE_size; i++) {
230 old_chi_inv[i][
ALL] = 0;
235 : mh(_mh), D(d), D_h(d, _mh), gauge(g) {
240 : mh(_mh), D(d), D_h(d, _mh), gauge(g) {
242 setup(mre_guess_size);
246 : mh(fa.mh), D(fa.D), D_h(fa.D_h), gauge(fa.gauge) {
264 D_h.dagger(chi, psi);
265 inverse.
apply(psi, v);
286 inverse.
apply(psi, v);
303 psi[X].gaussian_random();
307 inverse_h.
apply(v, psi);
317 MRE_guess(psi, chi, D, old_chi_inv);
320 if constexpr (std::is_same<double, typename gauge_field::basetype>::value) {
321 hila::out0 <<
"Starting with single precision inversion\n";
323 auto single_precision = gauge.get_single_precision();
324 typename DIRAC_OP::type_flt D_flt(D, single_precision);
332 D_flt.dagger(t1, t2);
340 for (
int i = 1; i < MRE_size; i++) {
341 old_chi_inv[i] = old_chi_inv[i - 1];
343 old_chi_inv[0] = psi;
360 D_h.dagger(chi, Dhchi);
363 inverse.
apply(Dhchi, psi);
368 Mpsi[D.par] = Mpsi[X] - chi[X];
370 D.force(Mpsi, psi, force, 1);
371 D.force(psi, Mpsi, force2, -1);
373 foralldir(dir) { force[dir][
ALL] = -eps * (force[dir][X] + force2[dir][X]); }
hila::arithmetic_type< T > squarenorm(const Array< n, m, T > &rhs)
Return square norm of Array.
The conjugate gradient operator. Applies the inverse square of an operator on a vector.
void apply(Field< vector_type > &in, Field< vector_type > &out)
The field class implements the standard methods for accessing Fields. Hilapp replaces the parity acce...
void set_boundary_condition(Direction dir, hila::bc bc)
Set the boundary condition in a given Direction (periodic or antiperiodic)
Field< A > dagger() const
Returns dagger or Hermitian conjugate of Field depending on how it is defined for Field type T.
void copy_boundary_condition(const Field< A > &rhs)
Copy the boundary condition from another field.
void force_step(double eps)
void draw_gaussian_fields()
double action()
Calculate and return the action.
void draw_gaussian_fields()
void initial_guess(Field< vector_type > &chi, Field< vector_type > &psi)
void force_step(double eps)
void action(Field< double > &S)
Return the action as a field of double precision numbers.
void save_new_solution(Field< vector_type > &psi)
Add new solution to the list.
Matrix class which defines matrix operations.
void draw_gaussian_fields()
void action(Field< double > &S)
Calculate the action as a field of double precision numbers.
void save_new_solution(Field< vector_type > &psi)
Add new solution to the list for MRE.
void force_step(double eps)
void initial_guess(Field< vector_type > &chi, Field< vector_type > &psi)
virtual void refresh()
Recalculate represented or smeared field.
void add_momentum(Field< SquareMatrix< N, Complex< basetype > > > *force)
constexpr Parity EVEN
bit pattern: 001
#define foralldir(d)
Macro to loop over (all) Direction(s)
constexpr Parity ALL
bit pattern: 011
std::ostream out0
This writes output only from main process (node 0)