From 026e736dfabdb256056a5fc6dc31d443556a5bfc Mon Sep 17 00:00:00 2001 From: Alessandro Lupo Date: Mon, 3 Apr 2023 16:31:19 +0100 Subject: [PATCH] Projection on algebra can now be templated. Fix #12 --- Grid/lattice/Lattice_ET.h | 2 + Grid/qcd/utils/Sp2n.impl | 24 +++- Grid/tensors/Tensor_Ta.h | 80 ++++++++++++ tests/sp2n/Test_project_on_Sp.cc | 211 +++++++++++++++++++++++-------- 4 files changed, 261 insertions(+), 56 deletions(-) diff --git a/Grid/lattice/Lattice_ET.h b/Grid/lattice/Lattice_ET.h index 9042eb8f..661d7441 100644 --- a/Grid/lattice/Lattice_ET.h +++ b/Grid/lattice/Lattice_ET.h @@ -345,6 +345,7 @@ GridUnopClass(UnaryNot, Not(a)); GridUnopClass(UnaryTrace, trace(a)); GridUnopClass(UnaryTranspose, transpose(a)); GridUnopClass(UnaryTa, Ta(a)); +GridUnopClass(UnaryProjectSp2nAlgebra, ProjectSp2nAlgebra(a)); GridUnopClass(UnaryProjectOnGroup, ProjectOnGroup(a)); GridUnopClass(UnaryProjectOnSpGroup, ProjectOnSpGroup(a)); GridUnopClass(UnaryTimesI, timesI(a)); @@ -457,6 +458,7 @@ GRID_DEF_UNOP(operator!, UnaryNot); GRID_DEF_UNOP(trace, UnaryTrace); GRID_DEF_UNOP(transpose, UnaryTranspose); GRID_DEF_UNOP(Ta, UnaryTa); +GRID_DEF_UNOP(ProjectSp2nAlgebra, UnaryProjectSp2nAlgebra); GRID_DEF_UNOP(ProjectOnGroup, UnaryProjectOnGroup); GRID_DEF_UNOP(ProjectOnSpGroup, UnaryProjectOnSpGroup); GRID_DEF_UNOP(timesI, UnaryTimesI); diff --git a/Grid/qcd/utils/Sp2n.impl b/Grid/qcd/utils/Sp2n.impl index 77da9ad0..347eb3ce 100644 --- a/Grid/qcd/utils/Sp2n.impl +++ b/Grid/qcd/utils/Sp2n.impl @@ -274,8 +274,6 @@ static void OmegaInvariance(ColourMatrix &in) { Omega = Zero(); const int nsp=ncolour/2; - std::cout << GridLogMessage << "I am a ColourMatrix" << std::endl; - // for (int i = 0; i < ncolour; i++) wrong?! //{ // Omega()()(i, 2*ncolour-1-i) = 1.; @@ -314,8 +312,6 @@ static void OmegaInvariance(GaugeField &in) { Omega = Zero(); identity = 1.; - std::cout << GridLogMessage << "I am a GaugeField " << std::endl; - U = PeekIndex(in, 1); OmegaInvariance(U); @@ -333,8 +329,6 @@ static void OmegaInvariance(LatticeColourMatrixD &in) { Omega = Zero(); identity = 1.; - std::cout << GridLogMessage << "I am a LatticeColourMatrix " << std::endl; - for (int i = 0; i < nsp; i++) { Omega()()(i, nsp + i) = 1.; Omega()()(nsp + i, i) = -1; @@ -356,3 +350,21 @@ static void OmegaInvariance(LatticeColourMatrixD &in) { } } +template +static void Omega(LatticeColourMatrixD &in) { + const int nsp=ncolour/2; + LatticeColourMatrixD OmegaLatt(in.Grid()); + LatticeColourMatrixD identity(in.Grid()); + ColourMatrix Omega; + + OmegaLatt = Zero(); + Omega = Zero(); + identity = 1.; + + for (int i = 0; i < nsp; i++) { + Omega()()(i, nsp + i) = 1.; + Omega()()(nsp + i, i) = -1; + } + OmegaLatt = OmegaLatt + (identity * Omega); + in = OmegaLatt; +} diff --git a/Grid/tensors/Tensor_Ta.h b/Grid/tensors/Tensor_Ta.h index 2ee51fb4..87169ffc 100644 --- a/Grid/tensors/Tensor_Ta.h +++ b/Grid/tensors/Tensor_Ta.h @@ -66,6 +66,86 @@ template accelerator_inline iMatrix Ta(const iMatrix return ret; } +// for sp2n can't do something as simple as Ta. We do a Gram-Schmidt + +template accelerator_inline iScalar ProjectSp2nAlgebra(const iScalar&r) +{ + iScalar ret; + ret._internal = ProjectSp2nAlgebra(r._internal); + return ret; +} +template accelerator_inline iVector ProjectSp2nAlgebra(const iVector&r) +{ + iVector ret; + for(int i=0;i accelerator_inline iMatrix ProjectSp2nAlgebra(const iMatrix &arg) +{ + iMatrix ret; + vtype nrm; + vtype inner; + vtype tmp; + + for(int c1=0;c1 + prn += conjugate(ret._internal[c1][c])*ret._internal[b+N/2][c]; // + } + + + for(int c=0; c U_b + U_{b+N} ) + } + } + + zeroit(inner); + for(int c2=0;c2gSites(); std::vector pseeds({1,2,3,4,5}); - std::vector sseeds({6,7,8,9,10}); GridParallelRNG pRNG(&Grid); pRNG.SeedFixedIntegers(pseeds); - GridSerialRNG sRNG; sRNG.SeedFixedIntegers(sseeds); SU::HotConfiguration(pRNG,Umu); - U = PeekIndex(Umu,2); + U = PeekIndex(Umu,0); aux = U*adj(U) - identity; - std::cout <::OmegaInvariance(U); + std::cout << GridLogMessage << "Checking Omega invariance after ProjectOnSpGroup" << std::endl; + Sp::OmegaInvariance(U); // no assertion here, but the next check will kill us if we are not simplectic // checks on elements - std::cout <::ProjectOnGaugeGroup(U); + aux = U*adj(U) - identity; + std::cout << GridLogMessage << "U adjU - 1 = " << norm2(aux) << std::endl; + assert( norm2(aux) < 1e-8); + Sp::OmegaInvariance(U); + + std::cout << GridLogMessage << "Checking the structure is " << std::endl; + std::cout << GridLogMessage << "U = ( W X ) " << std::endl; + std::cout << GridLogMessage << " ( -X^* W^* ) " << std::endl; + std::cout <(U,c1,c2); + auto Wstar = PeekIndex(U,c1+nsp,c2+nsp); + auto Ww = conjugate( Wstar ); + auto amizero = sum(W - Ww); + auto amizeroo = TensorRemove(amizero); + assert( amizeroo.real() < 10e-6 ); + amizeroo *= i; + assert( amizeroo.real() < 10e-6 ); + } + + } - Complex a(25041994., 12.); - Complex b(39., 0.22); - Complex d(10000., -2222.3333); + for (int c1 = 0; c1 < nsp ; c1++) + { + for (int c2 = 0; c2 < nsp; c2++) + { + auto X = PeekIndex(U,c1,c2+nsp); + auto minusXstar = PeekIndex(U,c1+nsp,c2); + auto minusXx = conjugate(minusXstar); + auto amizero = sum (X + minusXx); + auto amizeroo = TensorRemove(amizero); + assert( amizeroo.real() < 10e-6 ); + amizeroo *= i; + assert( amizeroo.real() < 10e-6 ); + } + } + + std::cout << GridLogMessage << "Testing ProjectGn" << std::endl; + U = U + 2932.111*identity; + std::cout << GridLogMessage << "Apply ProjectGn to deformed matrix" << std::endl; + Sp::ProjectGn(U); + aux = U*adj(U) - identity; + std::cout << GridLogMessage << "U adjU - 1 = " << norm2(aux) << std::endl; + assert( norm2(aux) < 1e-8); + std::cout << GridLogMessage << "Det after ProjectGn = " << norm2( Determinant(U) ) / vol << std::endl; + assert( norm2(aux) - 1 < 1e-8); + Sp::OmegaInvariance(U); + + std::cout << GridLogMessage << "Checking the structure is " << std::endl; + std::cout << GridLogMessage << "U = ( W X ) " << std::endl; + std::cout << GridLogMessage << " ( -X^* W^* ) " << std::endl; + std::cout <(U,c1,c2); + auto Wstar = PeekIndex(U,c1+nsp,c2+nsp); + auto Ww = conjugate( Wstar ); + auto amizero = sum(W - Ww); + auto amizeroo = TensorRemove(amizero); + assert( amizeroo.real() < 10e-6 ); + amizeroo *= i; + assert( amizeroo.real() < 10e-6 ); + } + + } + + for (int c1 = 0; c1 < nsp ; c1++) + { + for (int c2 = 0; c2 < nsp; c2++) + { + auto X = PeekIndex(U,c1,c2+nsp); + auto minusXstar = PeekIndex(U,c1+nsp,c2); + auto minusXx = conjugate(minusXstar); + auto amizero = sum (X + minusXx); + auto amizeroo = TensorRemove(amizero); + assert( amizeroo.real() < 10e-6 ); + amizeroo *= i; + assert( amizeroo.real() < 10e-6 ); + } + } + + std::cout << GridLogMessage << "Testing ProjectSp2nAlgebra" << std::endl; + + U = PeekIndex(Umu,1); + U = U + 666.*identity; + aux = U*adj(U) - identity; + std::cout << GridLogMessage << "Matrix deformed " << std::endl; + std::cout << GridLogMessage << "U adjU - 1 = " << norm2(aux) << std::endl; + std::cout << GridLogMessage << "Apply ProjectSp2nAlgebra to deformed matrix" << std::endl; + U = ProjectSp2nAlgebra(U); + aux = U*adj(U) - identity; + std::cout << GridLogMessage << "U adjU - 1 = " << norm2(aux) << std::endl; + assert( norm2(aux) < 1e-8); + std::cout << GridLogMessage << "Check that Omega U Omega = conj(U)" << std::endl; + + LatticeColourMatrixD Omega(&Grid); + + Sp::Omega(Omega); + aux = Omega*U*Omega - conjugate(U); + std::cout << GridLogMessage << "Omega U Omega - conj(U) = " << norm2(aux) << std::endl; + assert( norm2(aux) < 1e-8); + + + std::cout << GridLogMessage << "Checking the structure is " << std::endl; + std::cout << GridLogMessage << "U = ( W X ) " << std::endl; + std::cout << GridLogMessage << " ( X^* -W^* ) " << std::endl; + std::cout <(U,c1,c2); + auto Wstar = PeekIndex(U,c1+nsp,c2+nsp); + auto Ww = conjugate( Wstar ); + auto amizero = sum(W + Ww); + auto amizeroo = TensorRemove(amizero); + assert( amizeroo.real() < 10e-6 ); + amizeroo *= i; + assert( amizeroo.real() < 10e-6 ); + } + + } + + for (int c1 = 0; c1 < nsp ; c1++) + { + for (int c2 = 0; c2 < nsp; c2++) + { + auto X = PeekIndex(U,c1,c2+nsp); + auto minusXstar = PeekIndex(U,c1+nsp,c2); + auto minusXx = conjugate(minusXstar); + auto amizero = sum (X - minusXx); + auto amizeroo = TensorRemove(amizero); + assert( amizeroo.real() < 10e-6 ); + amizeroo *= i; + assert( amizeroo.real() < 10e-6 ); + } + } + - A()()(0,0) = a; - A()()(0,1) = b; - A()()(1,0) = i; - A()()(1,1) = d; - std::cout <