Something went wrong on our end
-
Bertram Kopf authored73f9787b
IsobarTensorPsiToGamXDecay.cc 18.40 KiB
//************************************************************************//
// //
// Copyright 2013 Bertram Kopf (bertram@ep1.rub.de) //
// Julian Pychy (julian@ep1.rub.de) //
// - Ruhr-Universität Bochum //
// //
// This file is part of Pawian. //
// //
// Pawian is free software: you can redistribute it and/or modify //
// it under the terms of the GNU General Public License as published by //
// the Free Software Foundation, either version 3 of the License, or //
// (at your option) any later version. //
// //
// Pawian is distributed in the hope that it will be useful, //
// but WITHOUT ANY WARRANTY; without even the implied warranty of //
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the //
// GNU General Public License for more details. //
// //
// You should have received a copy of the GNU General Public License //
// along with Pawian. If not, see <http://www.gnu.org/licenses/>. //
// //
//************************************************************************//
// IsobarTensorPsiToGamXDecay class definition file. -*- C++ -*-
// Copyright 2014 Bertram Kopf
#include <getopt.h>
#include <fstream>
#include <algorithm>
#include "PwaUtils/IsobarTensorPsiToGamXDecay.hh"
#include "qft++/relativistic-quantum-mechanics/Utils.hh"
#include "qft++Extension/PawianUtils.hh"
#include "ErrLogger/ErrLogger.hh"
#include "Particle/Particle.hh"
#include "Utils/PawianCollectionUtils.hh"
#include "Utils/FunctionUtils.hh"
#include "PwaUtils/KinUtils.hh"
#include "PwaUtils/EvtDataBaseList.hh"
#include "PwaUtils/GlobalEnv.hh"
#include "PwaUtils/AbsDynamics.hh"
#include "PwaUtils/DynRegistry.hh"
#include "PwaUtils/ProdChannelInfo.hh"
#include "ConfigParser/ParserBase.hh"
IsobarTensorPsiToGamXDecay::IsobarTensorPsiToGamXDecay(Particle* mother, Particle* daughter1_gamma, Particle* daughter2, ChannelID channelID) :
IsobarTensorDecay(mother, daughter1_gamma, daughter2, channelID, "IsobarTensorPsiToGamXDecay")
,_XisEven(false)
,_noOfAmps(0)
{
if(mother->twoIso() !=0 || mother->theParity() != -1 || mother->twoJ() != 2 || mother->theParity() != -1 || mother->theCParity() || mother->mass() < 0.01){
Alert << "mother particle does not have the quantum number combinations JPC=1-- or its mass is below 0.01 GeV/c2 !!!" << endmsg;
exit(0);
}
if(daughter1_gamma->twoJ() != 2 || daughter1_gamma->theParity() != -1 || daughter1_gamma->theCParity() || daughter1_gamma->mass() > 1.e-6){
Alert << "daughter particle 1 is not a photon" << endmsg;
exit(0);
}
if(daughter2->twoJ()%4 == 0) _XisEven=true;
if(!_XisEven && mother->theParity() == -1 && daughter2->twoJ()>=6){
Alert << "radiative decays of Psi -> odd^- + gamma with J>=3 are not supported so far" << endmsg;
exit(0);
}
if(!_XisEven && mother->theParity() == 1 && daughter2->twoJ()>=6){
Alert << "radiative decays of Psi -> odd^+ + gamma with J>=3 are not supported so far" << endmsg;
exit(0);
}
if (daughter2->twoJ()==0) _noOfAmps=1;
else if(daughter2->twoJ()==2) _noOfAmps=2;
else _noOfAmps=3;
InfoMsg << "daughter2->twoJ()%2 = " << daughter2->twoJ()%2 << "_XisEven: " << _XisEven << " daughter2->theParity(): " << daughter2->theParity() << endmsg;
fillAmpLMap();
}
IsobarTensorPsiToGamXDecay::IsobarTensorPsiToGamXDecay(std::shared_ptr<const IGJPC> motherIGJPCPtr, Particle* daughter1_gamma, Particle* daughter2, ChannelID channelID, std::string motherName) :
IsobarTensorDecay(motherIGJPCPtr, daughter1_gamma, daughter2, channelID, motherName, "IsobarTensorPsiToGamXDecay")
,_XisEven(false)
{
if(motherIGJPCPtr->I != 0 || motherIGJPCPtr->G != -1 || motherIGJPCPtr->J != 1 || motherIGJPCPtr->P != -1 || motherIGJPCPtr->C != -1 ){
Alert << "mother particle does not have the quantum number combinations IG(JPC)=0-(1--) !!!" << endmsg;
exit(0);
}
if(daughter1_gamma->twoJ() != 2 || daughter1_gamma->theParity() != -1 || daughter1_gamma->theCParity() !=-1 || daughter1_gamma->mass() > 1.e-6){
Alert << "daughter particle 1 is not a photon" << endmsg;
Alert << "daughter1_gamma->twoJ(): " << daughter1_gamma->twoJ() << "\n"
<< "daughter1_gamma->theParity(): " << daughter1_gamma->theParity() << "\n"
<< "daughter1_gamma->theCParity(): " << daughter1_gamma->theCParity() << "\n"
<< "daughter1_gamma->mass(): " << daughter1_gamma->mass() << endmsg;
exit(0);
}
if(daughter2->twoJ()%4 ==0) _XisEven=true;
if(!_XisEven && motherIGJPCPtr->P == -1 && daughter2->twoJ()>=6){
Alert << "radiative decays of Psi -> odd^- + gamma with J>=3 are not supported so far" << endmsg;
exit(0);
}
if(!_XisEven && motherIGJPCPtr->P == 1 && daughter2->twoJ()>=6){
Alert << "radiative decays of Psi -> odd^+ + gamma with J>=3 are not supported so far" << endmsg;
exit(0);
}
if (daughter2->twoJ()==0) _noOfAmps=1;
else if(daughter2->twoJ()==2) _noOfAmps=2;
else _noOfAmps=3;
InfoMsg << "daughter2->twoJ()%2 = " << daughter2->twoJ()%2 << "_XisEven: " << _XisEven << " daughter2->theParity(): " << daughter2->theParity() << endmsg;
fillAmpLMap();
}
IsobarTensorPsiToGamXDecay::~IsobarTensorPsiToGamXDecay(){
}
void IsobarTensorPsiToGamXDecay::print(std::ostream& os) const{
os << "\nJPCLS tensor amplitudes for decay\t" << _name << ":\n";
os << "suffix for fit parameter name:\t" << _fitParamSuffix << "\n";
std::vector< std::shared_ptr<const JPCLS> >::const_iterator it;
for (it = _JPCLSDecAmps.begin(); it!= _JPCLSDecAmps.end(); ++it){
(*it)->print(os);
os << "\n";
}
AbsDecay::print(os);
os << "\n";
}
void IsobarTensorPsiToGamXDecay::fillWignerDs(std::map<std::string, Vector4<double> >& fsMap, Vector4<double>& prodParticle4Vec, EvtData* evtData){
int evtNo=evtData->evtNo;
std::map<int, bool>::const_iterator it = _alreadyFilledMap.find(evtNo);
if(it!=_alreadyFilledMap.end() && it->second) return; //already filled
Vector4<double> all4Vec(0.,0.,0.,0.);
//fill all4Vec
std::map<std::string , Vector4<double> >::iterator itMap;
for(itMap=fsMap.begin(); itMap!=fsMap.end(); ++itMap){
all4Vec+=itMap->second;
}
//fill daughter1 and daughter2 4Vec
Vector4<double> daughter1Gam_4Vec(0.,0.,0.,0.);
itMap=fsMap.find( _daughter1->name() );
if(itMap!=fsMap.end()) daughter1Gam_4Vec=itMap->second;
else {
Alert << "particle with the name " << _daughter1->name() << " can not be found in the list of final state particles!!!" << endmsg;
exit(0);
}
Vector4<double> daughter2_4Vec(0.,0.,0.,0.);
std::vector<Particle*> finalStatePart2;
if(0!=_absDecDaughter2) finalStatePart2=_absDecDaughter2->finalStateParticles();
else finalStatePart2.push_back(_daughter2);
std::vector<Particle*>::iterator itParticle;
for (itParticle= finalStatePart2.begin(); itParticle != finalStatePart2.end(); ++itParticle){
itMap=fsMap.find( (*itParticle)->name() );
daughter2_4Vec+=itMap->second;
}
if(_isProdAmp){
if (!_daughter2IsStable) _absDecDaughter2->fillWignerDs(fsMap, daughter2_4Vec, evtData);
}
else{
if (!_daughter2IsStable) _absDecDaughter2->fillWignerDs(fsMap, prodParticle4Vec, evtData);
}
Vector4<double> mother_4Vec=daughter1Gam_4Vec+daughter2_4Vec;
Vector4<double> daughter1GamTensor4Vec=daughter1Gam_4Vec;
Vector4<double> daughter2Tensor4Vec=daughter2_4Vec;
Vector4<double> motherTensor4Vec=mother_4Vec;
daughter1GamTensor4Vec.Boost(all4Vec);
daughter2Tensor4Vec.Boost(all4Vec);
motherTensor4Vec.Boost(all4Vec);
Vector4<double> daughter2HelMother(0.,0.,0.,0.);
if(_hasMotherPart){
if(fabs(mother_4Vec==all4Vec)){
daughter2HelMother=daughter2_4Vec;
daughter2HelMother.Boost(daughter2HelMother); //is this correct????
}
else daughter2HelMother=helicityVec(prodParticle4Vec, mother_4Vec, daughter2_4Vec);
}
else{
daughter2HelMother=daughter2_4Vec;
daughter2HelMother.Boost(mother_4Vec);
}
Spin spinMother(1);
Spin spinDaughter1Gam(1);
Spin spinDaughter2=_daughter2IGJPCPtr->J;
double motherMass=motherTensor4Vec.M();
if (motherMass<1.e-5) motherMass=0.;
else if(motherMass != motherMass) motherMass=0.;
_polMother.SetP4(motherTensor4Vec, motherMass);
double daughter1GamMass=0.;
double daughter2Mass=daughter2Tensor4Vec.M();
if(daughter2Mass!=daughter2Mass || daughter2Mass < 1.e-5) daughter2Mass=0.;
_polDaughter1.SetP4(daughter1GamTensor4Vec, daughter1GamMass);
_polDaughter2.SetP4(daughter2Tensor4Vec, daughter2Mass);
Tensor<complex<double> > S_alpha_beta= (_lctTensor*daughter1GamTensor4Vec)*motherTensor4Vec;
Tensor<complex<double> > currentAmp1;
Tensor<complex<double> > currentAmp2;
Tensor<complex<double> > currentAmp3;
Spin lamMotherMax=spinMother;
for (Spin lamMother=-lamMotherMax; lamMother<=lamMotherMax; ++lamMother){
for (Spin lam1Gam=-1; lam1Gam<=1; lam1Gam+=2){
Tensor<complex<double> > PsiGamPolProj=_polMother(lamMother)%conj(_polDaughter1(lam1Gam));
for (Spin mX=-spinDaughter2; mX<=spinDaughter2; ++mX){
Tensor<complex<double> > PpsySpinProjX_jg0=conj(_polDaughter2(mX));
Tensor<complex<double> > PpsySpinProjX_jg1=conj(_polDaughter2(mX));
Tensor<complex<double> > PpsySpinProjX_jg2=conj(_polDaughter2(mX));
if(spinDaughter2>0){
//J contractions
for (int i=0; i<spinDaughter2; ++i) PpsySpinProjX_jg0*=motherTensor4Vec;
}
if(spinDaughter2>1){
//J-1 contractions
for (int i=0; i<spinDaughter2-1; ++i) PpsySpinProjX_jg1*=motherTensor4Vec;
}
if(spinDaughter2>2){
//J-2 contractions
for (int i=0; i<spinDaughter2-2; ++i) PpsySpinProjX_jg2*=motherTensor4Vec;
}
DebugMsg << "PpsySpinProjX_jg0.Rank(): " << PpsySpinProjX_jg0.Rank() << "\nval: " << PpsySpinProjX_jg0 << endmsg;
DebugMsg << "PpsySpinProjX_jg1.Rank(): " << PpsySpinProjX_jg1.Rank() << "\nval: " << PpsySpinProjX_jg1 << endmsg;
DebugMsg << "PpsySpinProjX_jg2.Rank(): " << PpsySpinProjX_jg2.Rank() << "\nval: " << PpsySpinProjX_jg2 << endmsg;
//case J^PC(X)=0+, 2+, 4+, ... and 1-, 3-, ...
if((_XisEven && _daughter2IGJPCPtr->P==1) || (!_XisEven && _daughter2IGJPCPtr->P==-1) ){ //0++, 2++, 4++, ...
//first amplitude
MetricTensor g_munu;
currentAmp1=(PsiGamPolProj | g_munu) * PpsySpinProjX_jg0;
// if(_daughter2->twoJ()>=4) currentAmp1 *= PpsySpinProjX_jg2 | (motherTensor4Vec%motherTensor4Vec);
DebugMsg << "currentAmp1.Rank(): " << currentAmp1.Rank() << "\nval: " << currentAmp1 << endmsg;
Id3StringType IdLamMotherLamGamLamX=FunctionUtils::spin3Index(lamMother, lam1Gam, mX);
// evtData->ComplexDoubleInt3SpinString[_name][0][lamMother][lam1Gam][mX]=currentAmp1(0);
evtData->ComplexN3Spin[_nameId][0][IdLamMotherLamGamLamX]=currentAmp1(0);
if(_noOfAmps>1){
//second amplitude
currentAmp2=(_polMother(lamMother)*daughter1GamTensor4Vec)*( conj(_polDaughter1(lam1Gam)) | PpsySpinProjX_jg1 );
DebugMsg << "currentAmp2.Rank(): " << currentAmp2.Rank() << "\nval: " << currentAmp2 << endmsg;
//evtData->ComplexDoubleInt3SpinString[_name][1][lamMother][lam1Gam][mX]=currentAmp2(0);
evtData->ComplexN3Spin[_nameId][1][IdLamMotherLamGamLamX]=currentAmp2(0);
if(_noOfAmps>2){
//3. amplitude
currentAmp3= PsiGamPolProj | PpsySpinProjX_jg2;
DebugMsg << "currentAmp3.Rank(): " << currentAmp3.Rank() << "\nval: " << currentAmp3 << endmsg;
// evtData->ComplexDoubleInt3SpinString[_name][2][lamMother][lam1Gam][mX]=currentAmp3(0);
evtData->ComplexN3Spin[_nameId][2][IdLamMotherLamGamLamX]=currentAmp3(0);
}
}
}
// //case J^PC(X)=1+, 3+, 5+, ...
// if(!_XisEven && _daughter2IGJPCPtr->P==1){
// //1. amplitude
// Tensor<complex<double> > U_numu1= (_lctTensor*PpsySpinProjX_jg1)*motherTensor4Vec;
// currentAmp1 = PsiGamPolProj | U_numu1;
// DebugMsg << "currentAmp1.Rank(): " << currentAmp1.Rank() << "\nval: " << currentAmp1(0) << endmsg;
// evtData->ComplexDoubleInt3SpinString[_name][0][lamMother][lam1Gam][mX]=currentAmp1(0);
// //2. amplitude
// Tensor<complex<double> > U_numu2= daughter1GamTensor4Vec % (S_alpha_beta*PpsySpinProjX_jg1);
// currentAmp2=PsiGamPolProj | U_numu2;
// DebugMsg << "currentAmp2.Rank(): " << currentAmp2.Rank() << "\nval: " << currentAmp2(0) << endmsg;
// evtData->ComplexDoubleInt3SpinString[_name][1][lamMother][lam1Gam][mX]=currentAmp2(0);
// if(spinDaughter2>1){
// //3. amplitude ?????
// currentAmp2=complex<double>(0.,0.);
// evtData->ComplexDoubleInt3SpinString[_name][2][lamMother][lam1Gam][mX]=complex<double>(0.,0.);
// }
// }
//case J^PC(X)=0-, 2-, 4-, ... and 1+, 3+, ...
if((_XisEven && _daughter2IGJPCPtr->P==-1) || (!_XisEven && _daughter2IGJPCPtr->P==1)){ //0-, 2-, 4-, ...
//if(_XisEven && _daughter2IGJPCPtr->P==-1){
//1. amplitude
Tensor<complex<double> > U_numu1;
U_numu1 = S_alpha_beta*PpsySpinProjX_jg0;
currentAmp1=PsiGamPolProj | U_numu1;
DebugMsg << "currentAmp1.Rank(): " << currentAmp1.Rank() << "\nval: " << currentAmp1(0) << endmsg;
// evtData->ComplexDoubleInt3SpinString[_name][0][lamMother][lam1Gam][mX]=currentAmp1(0);
Id3StringType IdLamMotherLamGamLamX=FunctionUtils::spin3Index(lamMother, lam1Gam, mX);
// evtData->ComplexDoubleInt3SpinString[_name][0][lamMother][lam1Gam][mX]=currentAmp1(0);
evtData->ComplexN3Spin[_nameId][0][IdLamMotherLamGamLamX]=currentAmp1(0);
if(spinDaughter2>0){
//2. amplitude
Tensor<complex<double> > U_numu2= daughter1GamTensor4Vec % (S_alpha_beta*PpsySpinProjX_jg1);
currentAmp2=PsiGamPolProj | U_numu2;
DebugMsg << "currentAmp2.Rank(): " << currentAmp2.Rank() << "\nval: " << currentAmp2(0) << endmsg;
// evtData->ComplexDoubleInt3SpinString[_name][1][lamMother][lam1Gam][mX]=currentAmp2(0);
evtData->ComplexN3Spin[_nameId][1][IdLamMotherLamGamLamX]=currentAmp2(0);
if(spinDaughter2>1){
//3. amplitude ?????
Tensor<complex<double> > U_numu3= (_lctTensor*(PpsySpinProjX_jg2*daughter1GamTensor4Vec))*motherTensor4Vec;
// Tensor<complex<double> > U_numu3= _lctTensor | PpsySpinProjX_jg2;
currentAmp3=PsiGamPolProj | U_numu3;
// evtData->ComplexDoubleInt3SpinString[_name][2][lamMother][lam1Gam][mX]=currentAmp3(0);
evtData->ComplexN3Spin[_nameId][2][IdLamMotherLamGamLamX]=currentAmp3(0);
}
}
}
// //case J^PC(X)=1-, 3-, 5-, ...
// if(!_XisEven && _daughter2IGJPCPtr->P==-1){ //??????????????
// MetricTensor g_munu;
// //1. amplitude
// DebugMsg << "S_alpha_beta*PpsySpinProjX_jg1: " << S_alpha_beta*PpsySpinProjX_jg1 << endmsg;
// DebugMsg << "(S_alpha_beta*PpsySpinProjX_jg1)*motherTensor4Vec: " << (S_alpha_beta*PpsySpinProjX_jg1)*motherTensor4Vec << endmsg;
// DebugMsg << "S_alpha_beta*motherTensor4Vec: " << S_alpha_beta*motherTensor4Vec << endmsg;
// DebugMsg << "(S_alpha_beta*motherTensor4Vec)*PpsySpinProjX_jg1: " << (S_alpha_beta*motherTensor4Vec)*PpsySpinProjX_jg1 << endmsg;
// DebugMsg << "(S_alpha_beta*PpsySpinProjX_jg1)*daughter1GamTensor4Vec: " << (S_alpha_beta*PpsySpinProjX_jg1)*daughter1GamTensor4Vec << endmsg;
// Tensor<complex<double> > U_numu1= g_munu*((S_alpha_beta*PpsySpinProjX_jg1)*motherTensor4Vec);
// DebugMsg << "U_numu1: " << U_numu1 << endmsg;
// currentAmp1 = PsiGamPolProj | U_numu1;
// DebugMsg << "currentAmp1.Rank(): " << currentAmp1.Rank() << "\nval: " << currentAmp1(0) << endmsg;
// evtData->ComplexDoubleInt3SpinString[_name][0][lamMother][lam1Gam][mX]=currentAmp1(0);
// //2. amplitude
// DebugMsg << "((_lctTensor*PpsySpinProjX_jg1)*motherTensor4Vec)*motherTensor4Vec: " << ((_lctTensor*PpsySpinProjX_jg1)*motherTensor4Vec)*motherTensor4Vec << endmsg;
// DebugMsg << "(_lctTensor*PpsySpinProjX_jg1)*motherTensor: " << (_lctTensor*PpsySpinProjX_jg1)*motherTensor4Vec << endmsg;
// Tensor<complex<double> > U_numu2= daughter1GamTensor4Vec % (((_lctTensor*PpsySpinProjX_jg1)*motherTensor4Vec)*motherTensor4Vec);
// currentAmp2=PsiGamPolProj | U_numu2;
// DebugMsg << "currentAmp2.Rank(): " << currentAmp2.Rank() << "\nval: " << currentAmp2(0) << endmsg;
// evtData->ComplexDoubleInt3SpinString[_name][1][lamMother][lam1Gam][mX]=currentAmp2(0);
// if(spinDaughter2>1){
// //3. amplitude ?????
// currentAmp2=complex<double>(0.,0.);
// evtData->ComplexDoubleInt3SpinString[_name][2][lamMother][lam1Gam][mX]=complex<double>(0.,0.);
// }
// }
}
}
}
bool fillqVals=false;
if(_isProdAmp && _useProdBarrier) fillqVals=true;
else if(0!=_absDynPtr){
if(_absDynPtr->type()=="BlattWBarrierTensorDynamics") fillqVals=true;
}
if(fillqVals){
double qVal=daughter2HelMother.P();
double qValNorm=PawianQFT::breakupMomQDefault(mother_4Vec.M(), massSumFsParticlesDec1(), massSumFsParticlesDec2()).real();
evtData->DoubleMassId[_wignerDqId]=qVal;
evtData->DoubleMassId[_wignerDqNormId]=qValNorm;
}
}
void IsobarTensorPsiToGamXDecay::fillAmpLMap(){
//case J^PC(X)=0+, 2+, 4+, ... and 1-, 3-, ...
if((_XisEven && _daughter2IGJPCPtr->P==1) || (!_XisEven && _daughter2IGJPCPtr->P==-1) ){
_ampLMap[0]=_daughter2IGJPCPtr->J;
if(_noOfAmps>1) _ampLMap[1]=_daughter2IGJPCPtr->J;
if(_noOfAmps>2) _ampLMap[2]=_daughter2IGJPCPtr->J-2;
}
else{ //case J^PC(X)=0-, 2-, 4-, ... and 1+, 3+, ...
_ampLMap[0]=_daughter2IGJPCPtr->J+1;
if(_noOfAmps>1) _ampLMap[1]=_daughter2IGJPCPtr->J+1;
if(_noOfAmps>2) _ampLMap[2]=_daughter2IGJPCPtr->J-1;
}
}
void IsobarTensorPsiToGamXDecay::enableProdBarrier(){
if(_dynEnabled){
Alert << "dynamics already enabled for " << name() << endmsg;
exit(1);
}
if(!_prodChannelInfo->isProductionChannel()){
WarningMsg << name() << " is not a production amplitide! Barrier factors for the production can not be enabled!" << endmsg;
return;
}
if(!_prodChannelInfo->withProdBarrier()){
WarningMsg << name() << "production barrier disabled" << endmsg;
return;
}
if(_prodChannelInfo->prodBarrierType()!="BlattWBarrierTensor"){
Alert << name() << "production barrier enabled with type " << _prodChannelInfo->prodBarrierType()
<< "\tIsobarTensorPsiToGamXDecay only supports type BlattWBarrierTensor" << endmsg;
exit(1);
}
if(!_isProdAmp){
Alert << name() << " is not a production amplitide! Barrier factors for the production can not be enabled!" << endmsg;
exit(1);
}
_useProdBarrier=true;
_dynType="BlattWBarrierTensor";
_qR=_prodChannelInfo->qRPod();
InfoMsg << "Barrier factors for production amplitude " << name() << " enabled!" << endmsg;
_absDynPtr=DynRegistry::instance()->getDynamics(shared_from_this());
_dynEnabled=true;
}