104G4int& G4RadioactiveDecay::NumberOfInstances()
106 static G4int numberOfInstances = 0;
107 return numberOfInstances;
113 forceDecayDirection(0.,0.,0.), forceDecayHalfAngle(0.*
deg), dirPath(
""),
119 G4cout <<
"G4RadioactiveDecay constructor: processName = " << processName
138 char* path_var = std::getenv(
"G4RADIOACTIVEDATA");
141 "Environment variable G4RADIOACTIVEDATA is not set");
144 std::ostringstream os;
146 std::ifstream testFile;
147 testFile.open(os.str() );
148 if (!testFile.is_open() )
150 "Environment variable G4RADIOACTIVEDATA is set, but does not point to correct directory");
157#ifdef G4MULTITHREADED
158 G4AutoLock lk(&G4RadioactiveDecay::radioactiveDecayMutex);
159 NumberOfInstances()++;
176 outFile <<
"The radioactive decay process (G4RadioactiveDecay) handles the\n"
177 <<
"alpha, beta+, beta-, electron capture and isomeric transition\n"
178 <<
"decays of nuclei (G4GenericIon) with masses A > 4.\n"
179 <<
"The required half-lives and decay schemes are retrieved from\n"
180 <<
"the RadioactiveDecay database which was derived from ENSDF.\n";
188 for (DecayTableMap::iterator i =
dkmap->begin(); i !=
dkmap->end(); i++) {
193#ifdef G4MULTITHREADED
194 G4AutoLock lk(&G4RadioactiveDecay::radioactiveDecayMutex);
195 --NumberOfInstances();
196 if(NumberOfInstances()==0)
198 for (DecayTableMap::iterator i = master_dkmap->begin(); i != master_dkmap->end(); i++) {
201 master_dkmap->clear();
211 if (((
const G4Ions*)(&aParticle))->GetExcitationEnergy() > 0.) {
return true;}
220 G4int A = ((
const G4Ions*) (&aParticle))->GetAtomicMass();
221 G4int Z = ((
const G4Ions*) (&aParticle))->GetAtomicNumber();
233 DecayTableMap::iterator table_ptr =
dkmap->find(key);
236 if (table_ptr ==
dkmap->end() ) {
238 if(theDecayTable) (*dkmap)[key] = theDecayTable;
240 theDecayTable = table_ptr->second;
242 return theDecayTable;
250 volume = theLogicalVolumes->
GetVolume(aVolume);
251 if (volume !=
nullptr)
258 G4cout <<
" Radioactive decay applied to " << aVolume <<
G4endl;
263 ed << aVolume <<
" is not a valid logical volume name."
264 <<
" Decay not activated for it."
266 G4Exception(
"G4RadioactiveDecay::SelectAVolume()",
"HAD_RDM_300",
276 volume = theLogicalVolumes->
GetVolume(aVolume);
277 if (volume !=
nullptr)
286 G4cout <<
" G4RadioactiveDecay::DeselectAVolume: " << aVolume
287 <<
" is removed from list " <<
G4endl;
292 ed << aVolume <<
" is not in the list. No action taken." <<
G4endl;
293 G4Exception(
"G4RadioactiveDecay::DeselectAVolume()",
"HAD_RDM_300",
300 ed << aVolume <<
" is not a valid logical volume name. No action taken."
302 G4Exception(
"G4RadioactiveDecay::DeselectAVolume()",
"HAD_RDM_300",
317 for (std::size_t i = 0; i < theLogicalVolumes->size(); ++i){
318 volume = (*theLogicalVolumes)[i];
356 G4cout <<
"G4RadioactiveDecay::GetMeanLifeTime() " <<
G4endl;
358 <<
" GeV, Mass: " << theParticle->
GetMass()/
GeV
359 <<
" GeV, Life time: " << theLife/
ns <<
" ns " <<
G4endl;
363 else if (theLife < 0.0) {meanlife =
DBL_MAX;}
364 else {meanlife = theLife;}
367 if (((
const G4Ions*)(theParticleDef))->GetExcitationEnergy() > 0. &&
368 meanlife ==
DBL_MAX) {meanlife = 0.;}
371 G4cout <<
" mean life time: " << meanlife/
s <<
" s " <<
G4endl;
393 G4cout <<
"G4RadioactiveDecay::GetMeanFreePath() " <<
G4endl;
395 <<
" GeV, Mass: " << aMass/
GeV <<
" GeV, tau: " << tau <<
" ns "
406 }
else if (tau < 0.0) {
409 ed <<
"Ion has negative lifetime " << tau
410 <<
" but is not stable. Setting mean free path to DBL_MAX" <<
G4endl;
411 G4Exception(
"G4RadioactiveDecay::GetMeanFreePath()",
"HAD_RDM_011",
418 pathlength =
c_light*tau*betaGamma;
424 G4cout <<
"G4Decay::GetMeanFreePath: "
426 <<
" stops, kinetic energy = "
436 G4cout <<
"mean free path: "<< pathlength/
m <<
" m" <<
G4endl;
475 os <<
"======================================================================"
477 os <<
"====== Radioactive Decay Physics Parameters ======="
479 os <<
"======================================================================"
481 os <<
"Max life time "
483 os <<
"Internal e- conversion flag "
485 os <<
"Stored internal conversion coefficients "
487 os <<
"Enable correlated gamma emission "
489 os <<
"Max 2J for sampling of angular correlations "
491 os <<
"Atomic de-excitation enabled "
492 << emparam->
Fluo() << endline;
493 os <<
"Auger electron emission enabled "
494 << emparam->
Auger() << endline;
495 os <<
"Check EM cuts disabled for atomic de-excitation "
497 os <<
"Use Bearden atomic level energies "
499 os <<
"Use ANSTO fluorescence model "
501 os <<
"Threshold for very long decay time at rest "
503 os <<
"======================================================================"
521 G4int A = ((
const G4Ions*)(&theParentNucleus))->GetAtomicMass();
522 G4int Z = ((
const G4Ions*)(&theParentNucleus))->GetAtomicNumber();
524 G4double levelEnergy = ((
const G4Ions*)(&theParentNucleus))->GetExcitationEnergy();
526 ((
const G4Ions*)(&theParentNucleus))->GetFloatLevelBase();
528#ifdef G4MULTITHREADED
529 G4AutoLock lk(&G4RadioactiveDecay::radioactiveDecayMutex);
532 DecayTableMap::iterator master_table_ptr = master_dkmap->find(key);
534 if (master_table_ptr != master_dkmap->end() ) {
535 return master_table_ptr->second;
543 std::ostringstream os;
544 os <<
dirPath <<
"/z" <<
Z <<
".a" <<
A <<
'\0';
551 std::ifstream DecaySchemeFile;
552 DecaySchemeFile.open(
file);
554 if (DecaySchemeFile.good()) {
558 G4double modeTotalBR[nMode] = {0.0};
560 for (
G4int i = 0; i < nMode; i++) {
564 char inputChars[120]={
' '};
585 while (!complete && !DecaySchemeFile.getline(inputChars, 120).eof()) {
588 G4Exception(
"G4RadioactiveDecay::LoadDecayTable()",
"HAD_RDM_100",
593 inputLine = inputChars;
595 if (inputChars[0] !=
'#' && inputLine.length() != 0) {
596 std::istringstream tmpStream(inputLine);
598 if (inputChars[0] ==
'P') {
601 tmpStream >> recordType >> parentExcitation >> floatingFlag >> dummy;
610 if (floatingLevel !=
noFloat) {
613 if (!floatMatch) found =
false;
622 if (inputLine.length() < 72) {
623 tmpStream >> theDecayMode >> dummy >> decayModeTotal;
624 switch (theDecayMode) {
631 theDecayTable->
Insert(anITChannel);
636 modeTotalBR[
BetaMinus] = decayModeTotal;
break;
638 modeTotalBR[
BetaPlus] = decayModeTotal;
break;
640 modeTotalBR[
KshellEC] = decayModeTotal;
break;
642 modeTotalBR[
LshellEC] = decayModeTotal;
break;
644 modeTotalBR[
MshellEC] = decayModeTotal;
break;
646 modeTotalBR[
NshellEC] = decayModeTotal;
break;
648 modeTotalBR[
Alpha] = decayModeTotal;
break;
650 modeTotalBR[
Proton] = decayModeTotal;
break;
652 modeTotalBR[
Neutron] = decayModeTotal;
break;
654 modeTotalBR[
SpFission] = decayModeTotal;
break;
668 modeTotalBR[
Triton] = decayModeTotal;
break;
672 G4Exception(
"G4RadioactiveDecay::LoadDecayTable()",
"HAD_RDM_000",
677 if (inputLine.length() < 84) {
678 tmpStream >> theDecayMode >> a >> daughterFloatFlag >> b >> c;
681 tmpStream >> theDecayMode >> a >> daughterFloatFlag >> b >> c >> betaType;
691 switch (theDecayMode) {
696 daughterFloatLevel, betaType);
699 theDecayTable->
Insert(aBetaMinusChannel);
708 daughterFloatLevel, betaType);
711 theDecayTable->
Insert(aBetaPlusChannel);
724 theDecayTable->
Insert(aKECChannel);
737 theDecayTable->
Insert(aLECChannel);
750 theDecayTable->
Insert(aMECChannel);
763 theDecayTable->
Insert(aNECChannel);
775 theDecayTable->
Insert(anAlphaChannel);
776 modeSumBR[
Alpha] += b;
787 theDecayTable->
Insert(aProtonChannel);
799 theDecayTable->
Insert(aNeutronChannel);
810 theDecayTable->
Insert(aSpontFissChannel);
852 theDecayTable->
Insert(aTritonChannel);
860 G4Exception(
"G4RadioactiveDecay::LoadDecayTable()",
"HAD_RDM_000",
878 theNuclearDecayChannel =
static_cast<G4NuclearDecay*
>(theChannel);
881 if (theDecayMode !=
IT) {
882 theBR = theChannel->
GetBR();
883 theChannel->
SetBR(theBR*modeTotalBR[theDecayMode]/modeSumBR[theDecayMode]);
888 DecaySchemeFile.close();
890 if (!found && levelEnergy > 0) {
897 theDecayTable->
Insert(anITChannel);
904#ifdef G4MULTITHREADED
907 return theDecayTable;
915 std::ifstream DecaySchemeFile(filename);
916 if (DecaySchemeFile) {
921 ed << filename <<
" does not exist! " <<
G4endl;
922 G4Exception(
"G4RadioactiveDecay::AddUserDecayDataFile()",
"HAD_RDM_001",
948 G4cout <<
"G4RadioactiveDecay::DecayIt : "
950 <<
" is not selected for the RDM"<<
G4endl;
972 G4cout <<
"G4RadioactiveDecay::DecayIt : "
974 <<
" is not an ion or is outside (Z,A) limits set for the decay. "
975 <<
" Set particle change accordingly. "
990 if (theDecayTable == 0 || theDecayTable->
entries() == 0) {
995 G4cout <<
"G4RadioactiveDecay::DecayIt : "
996 <<
"decay table not defined for "
998 <<
". Set particle change accordingly. "
1109 if (products->
entries() == 1) {
1142 if (temptime < 0.) temptime = 0.;
1143 finalGlobalTime += temptime;
1144 finalLocalTime += temptime;
1166 products->
Boost(ParentEnergy, ParentDirection);
1173 G4cout <<
"G4RadioactiveDecay::DecayAnalog: Decay vertex :";
1174 G4cout <<
" Time: " << finalGlobalTime/
ns <<
"[ns]";
1179 G4cout <<
"G4Decay::DecayIt : decay products in Lab. Frame" <<
G4endl;
1186 const G4int modelID_forAtomicRelaxation =
1188 for (
G4int index = 0; index < numberOfSecondaries; ++index ) {
1195 if ( index == numberOfSecondaries-1 ) {
1201 index < numberOfSecondaries-1 ) {
1234 if (theDecayChannel == 0) {
1238 G4Exception(
"G4RadioactiveDecay::DoDecay",
"HAD_RDM_013",
1244 G4cout <<
"G4RadioactiveDecay::DoIt : selected decay channel addr: "
1245 << theDecayChannel <<
G4endl;
1265 if (0 == products || 0 == products->
entries())
return;
1286 daughterType ==
neutron || daughterType == gamma ||
1294 G4cout <<
"CollimateDecayProduct for daughter "
1325 G4cout <<
" ChooseCollimationDirection returns " << dir <<
G4endl;
void G4Exception(const char *originOfException, const char *exceptionCode, G4ExceptionSeverity severity, const char *description)
std::ostringstream G4ExceptionDescription
static const G4double alpha
std::map< G4String, G4DecayTable * > DecayTableMap
@ G4RadioactiveDecayModeSize
static constexpr double m
static constexpr double s
static constexpr double keV
static constexpr double eV
static constexpr double nanosecond
static constexpr double GeV
static constexpr double MeV
static constexpr double pi
static constexpr double cm
static constexpr double deg
#define G4MUTEX_INITIALIZER
G4GLOB_DLL std::ostream G4cout
static G4Alpha * Definition()
G4DynamicParticle * PopProducts()
void Boost(G4double totalEnergy, const G4ThreeVector &momentumDirection)
G4VDecayChannel * GetDecayChannel(G4int index) const
void Insert(G4VDecayChannel *aChannel)
G4VDecayChannel * SelectADecayChannel(G4double parentMass=-1.)
G4bool CorrelatedGamma() const
G4bool StoreICLevelData() const
G4double GetMaxLifeTime() const
G4bool GetInternalConversionFlag() const
void SetMomentumDirection(const G4ThreeVector &aDirection)
const G4ThreeVector & GetMomentumDirection() const
const G4ParticleDefinition * GetParticleDefinition() const
G4ParticleDefinition * GetDefinition() const
G4double GetKineticEnergy() const
G4double GetTotalMomentum() const
void SetARM(G4bool onoff)
static G4Electron * Definition()
static G4EmParameters * Instance()
G4bool BeardenFluoDir() const
G4bool ANSTOFluoDir() const
G4bool DeexcitationIgnoreCut() const
static G4Gamma * Definition()
static G4GenericIon * GenericIon()
static G4HadronicParameters * Instance()
void RegisterExtraProcess(G4VProcess *)
void RegisterParticleForExtraProcess(G4VProcess *, const G4ParticleDefinition *)
static G4HadronicProcessStore * Instance()
void SetARM(G4bool onoff)
static G4Ions::G4FloatLevelBase FloatLevelBase(char flbChar)
G4LogicalVolume * GetVolume(const G4String &name, G4bool verbose=true, G4bool reverseSearch=false) const
static G4LogicalVolumeStore * GetInstance()
const G4String & GetName() const
static G4Neutron * Definition()
G4RadioactiveDecayMode GetDecayMode()
G4DeexPrecoParameters * GetParameters()
static G4NuclearLevelData * GetInstance()
void ProposeLocalTime(G4double t)
virtual void Initialize(const G4Track &)
void AddSecondary(G4Track *aSecondary)
G4bool GetPDGStable() const
const G4String & GetParticleType() const
G4double GetPDGMass() const
G4double GetPDGLifeTime() const
const G4String & GetParticleName() const
virtual void SetICM(G4bool)
virtual void RDMForced(G4bool)
static G4int GetModelID(const G4int modelIndex)
static G4Positron * Definition()
static G4Proton * Definition()
static const G4ThreeVector origin
std::map< G4int, G4String > theUserRadioactiveDataFiles
void SelectAVolume(const G4String &aVolume)
void DecayAnalog(const G4Track &theTrack)
G4RadioactiveDecayMessenger * theRadioactiveDecayMessenger
void StreamInfo(std::ostream &os, const G4String &endline)
void BuildPhysicsTable(const G4ParticleDefinition &)
std::vector< G4String > ValidVolumes
G4DecayTable * LoadDecayTable(const G4ParticleDefinition &theParentNucleus)
G4RadioactiveDecay(const G4String &processName="RadioactiveDecay")
G4double GetMeanLifeTime(const G4Track &theTrack, G4ForceCondition *condition)
G4DecayProducts * DoDecay(const G4ParticleDefinition &theParticleDef)
void CollimateDecayProduct(G4DynamicParticle *product)
G4NucleusLimits theNucleusLimits
G4double forceDecayHalfAngle
G4DecayTable * GetDecayTable(const G4ParticleDefinition *)
static const G4double levelTolerance
G4ParticleChangeForRadDecay fParticleChangeForRadDecay
G4ThreeVector forceDecayDirection
G4int GetVerboseLevel() const
G4double GetMeanFreePath(const G4Track &theTrack, G4double previousStepSize, G4ForceCondition *condition)
G4ThreeVector ChooseCollimationDirection() const
G4VParticleChange * DecayIt(const G4Track &theTrack, const G4Step &theStep)
G4bool IsApplicable(const G4ParticleDefinition &)
G4RadioactiveDecayMode theRadDecayMode
virtual void ProcessDescription(std::ostream &outFile) const
void DeselectAllVolumes()
void AddUserDecayDataFile(G4int Z, G4int A, G4String filename)
G4double fThresholdForVeryLongDecayTime
void DeselectAVolume(const G4String &aVolume)
void CollimateDecay(G4DecayProducts *products)
G4PhotonEvaporation * photonEvaporation
G4TrackStatus GetTrackStatus() const
G4VPhysicalVolume * GetVolume() const
G4double GetWeight() const
void SetWeight(G4double aValue)
const G4ThreeVector & GetPosition() const
void SetTouchableHandle(const G4TouchableHandle &apValue)
G4double GetGlobalTime() const
G4double GetLocalTime() const
const G4DynamicParticle * GetDynamicParticle() const
const G4TouchableHandle & GetTouchableHandle() const
void SetCreatorModelID(const G4int id)
void SetGoodForTrackingFlag(G4bool value=true)
static G4Triton * Definition()
void SetBR(G4double value)
virtual G4DecayProducts * DecayIt(G4double parentMass=-1.0)=0
void ProposeTrackStatus(G4TrackStatus status)
void ProposeWeight(G4double finalWeight)
void ProposeLocalEnergyDeposit(G4double anEnergyPart)
void SetNumberOfSecondaries(G4int totSecondaries)
G4LogicalVolume * GetLogicalVolume() const
void ClearNumberOfInteractionLengthLeft()
void SetProcessSubType(G4int)
G4VParticleChange * pParticleChange
static constexpr double ns
static constexpr double ps
void rstrip(G4String &str, char c=' ')
Remove trailing characters from string.