Geant4-11
Public Member Functions | Private Member Functions | Private Attributes
G4EmBiasingManager Class Reference

#include <G4EmBiasingManager.hh>

Public Member Functions

void ActivateForcedInteraction (G4double length=0.0, const G4String &r="")
 
void ActivateSecondaryBiasing (const G4String &region, G4double factor, G4double energyLimit)
 
G4double ApplySecondaryBiasing (std::vector< G4DynamicParticle * > &, const G4Track &track, G4VEmModel *currentModel, G4ParticleChangeForGamma *pParticleChange, G4double &eloss, G4int coupleIdx, G4double tcut, G4double safety=0.0)
 
G4double ApplySecondaryBiasing (std::vector< G4DynamicParticle * > &, const G4Track &track, G4VEmModel *currentModel, G4ParticleChangeForLoss *pParticleChange, G4double &eloss, G4int coupleIdx, G4double tcut, G4double safety=0.0)
 
G4double ApplySecondaryBiasing (std::vector< G4Track * > &, G4int coupleIdx)
 
G4bool CheckDirection (G4ThreeVector pos, G4ThreeVector momdir) const
 
G4bool ForcedInteractionRegion (G4int coupleIdx)
 
 G4EmBiasingManager ()
 
 G4EmBiasingManager (G4EmBiasingManager &)=delete
 
G4bool GetDirectionalSplitting ()
 
G4double GetStepLimit (G4int coupleIdx, G4double previousStep)
 
G4double GetWeight (G4int i)
 
void Initialise (const G4ParticleDefinition &part, const G4String &procName, G4int verbose)
 
G4EmBiasingManageroperator= (const G4EmBiasingManager &right)=delete
 
void ResetForcedInteraction ()
 
G4bool SecondaryBiasingRegion (G4int coupleIdx)
 
void SetDirectionalSplitting (G4bool v)
 
void SetDirectionalSplittingRadius (G4double r)
 
void SetDirectionalSplittingTarget (G4ThreeVector v)
 
 ~G4EmBiasingManager ()
 

Private Member Functions

G4double ApplyDirectionalSplitting (std::vector< G4DynamicParticle * > &vd, const G4Track &track, G4VEmModel *currentModel, G4int index, G4double tcut)
 
G4double ApplyDirectionalSplitting (std::vector< G4DynamicParticle * > &vd, const G4Track &track, G4VEmModel *currentModel, G4int index, G4double tcut, G4ParticleChangeForGamma *partChange)
 
void ApplyRangeCut (std::vector< G4DynamicParticle * > &vd, const G4Track &track, G4double &eloss, G4double safety)
 
G4double ApplyRussianRoulette (std::vector< G4DynamicParticle * > &vd, G4int index)
 
G4double ApplySplitting (std::vector< G4DynamicParticle * > &vd, const G4Track &track, G4VEmModel *currentModel, G4int index, G4double tcut)
 

Private Attributes

G4double currentStepLimit = 0.0
 
G4VEnergyLossProcesseIonisation = nullptr
 
G4bool fDirectionalSplitting = false
 
G4double fDirectionalSplittingRadius = 0.0
 
G4ThreeVector fDirectionalSplittingTarget
 
std::vector< G4doublefDirectionalSplittingWeights
 
std::vector< const G4Region * > forcedRegions
 
G4double fSafetyMin
 
std::vector< G4intidxForcedCouple
 
std::vector< G4intidxSecBiasedCouple
 
std::vector< G4doublelengthForRegion
 
std::vector< G4intnBremSplitting
 
G4int nForcedRegions = 0
 
G4int nSecBiasedRegions = 0
 
std::vector< G4doublesecBiasedEnegryLimit
 
std::vector< const G4Region * > secBiasedRegions
 
std::vector< G4doublesecBiasedWeight
 
G4bool startTracking = true
 
const G4ParticleDefinitiontheElectron
 
const G4ParticleDefinitiontheGamma
 
std::vector< G4DynamicParticle * > tmpSecondaries
 

Detailed Description

Definition at line 66 of file G4EmBiasingManager.hh.

Constructor & Destructor Documentation

◆ G4EmBiasingManager() [1/2]

G4EmBiasingManager::G4EmBiasingManager ( )

Definition at line 67 of file G4EmBiasingManager.cc.

68 : fDirectionalSplittingTarget(0.0,0.0,0.0)
69{
70 fSafetyMin = 1.e-6*mm;
73}
static constexpr double mm
Definition: G4SIunits.hh:95
static G4Electron * Electron()
Definition: G4Electron.cc:93
const G4ParticleDefinition * theGamma
G4ThreeVector fDirectionalSplittingTarget
const G4ParticleDefinition * theElectron
static G4Gamma * Gamma()
Definition: G4Gamma.cc:85

References G4Electron::Electron(), fSafetyMin, G4Gamma::Gamma(), mm, theElectron, and theGamma.

◆ ~G4EmBiasingManager()

G4EmBiasingManager::~G4EmBiasingManager ( )

Definition at line 77 of file G4EmBiasingManager.cc.

78{}

◆ G4EmBiasingManager() [2/2]

G4EmBiasingManager::G4EmBiasingManager ( G4EmBiasingManager )
delete

Member Function Documentation

◆ ActivateForcedInteraction()

void G4EmBiasingManager::ActivateForcedInteraction ( G4double  length = 0.0,
const G4String r = "" 
)

Definition at line 163 of file G4EmBiasingManager.cc.

165{
167 G4String name = rname;
168 if(name == "" || name == "world" || name == "World") {
169 name = "DefaultRegionForTheWorld";
170 }
171 const G4Region* reg = regionStore->GetRegion(name, false);
172 if(!reg) {
173 G4cout << "### G4EmBiasingManager::ForcedInteraction WARNING: "
174 << " G4Region <"
175 << rname << "> is unknown" << G4endl;
176 return;
177 }
178
179 // the region is in the list
180 if (0 < nForcedRegions) {
181 for (G4int i=0; i<nForcedRegions; ++i) {
182 if (reg == forcedRegions[i]) {
183 lengthForRegion[i] = val;
184 return;
185 }
186 }
187 }
188 if(val < 0.0) {
189 G4cout << "### G4EmBiasingManager::ForcedInteraction WARNING: "
190 << val << " < 0.0, so no activation for the G4Region <"
191 << rname << ">" << G4endl;
192 return;
193 }
194
195 // new region
196 forcedRegions.push_back(reg);
197 lengthForRegion.push_back(val);
199}
static const G4double reg
int G4int
Definition: G4Types.hh:85
#define G4endl
Definition: G4ios.hh:57
G4GLOB_DLL std::ostream G4cout
std::vector< const G4Region * > forcedRegions
std::vector< G4double > lengthForRegion
static G4RegionStore * GetInstance()
G4Region * GetRegion(const G4String &name, G4bool verbose=true) const
const char * name(G4int ptype)

References forcedRegions, G4cout, G4endl, G4RegionStore::GetInstance(), G4RegionStore::GetRegion(), lengthForRegion, G4InuclParticleNames::name(), nForcedRegions, and reg.

Referenced by G4VEnergyLossProcess::ActivateForcedInteraction(), and G4VEmProcess::ActivateForcedInteraction().

◆ ActivateSecondaryBiasing()

void G4EmBiasingManager::ActivateSecondaryBiasing ( const G4String region,
G4double  factor,
G4double  energyLimit 
)

Definition at line 204 of file G4EmBiasingManager.cc.

207{
208 //G4cout << "G4EmBiasingManager::ActivateSecondaryBiasing: "
209 // << rname << " F= " << factor << " E(MeV)= " << energyLimit/MeV
210 // << G4endl;
212 G4String name = rname;
213 if(name == "" || name == "world" || name == "World") {
214 name = "DefaultRegionForTheWorld";
215 }
216 const G4Region* reg = regionStore->GetRegion(name, false);
217 if(!reg) {
218 G4cout << "### G4EmBiasingManager::ActivateBremsstrahlungSplitting "
219 << "WARNING: G4Region <"
220 << rname << "> is unknown" << G4endl;
221 return;
222 }
223
224 // Range cut
225 G4int nsplit = 0;
226 G4double w = factor;
227
228 // splitting
229 if(factor >= 1.0) {
230 nsplit = G4lrint(factor);
231 w = 1.0/G4double(nsplit);
232
233 // Russian roulette
234 } else if(0.0 < factor) {
235 nsplit = 1;
236 w = 1.0/factor;
237 }
238
239 // the region is in the list - overwrite parameters
240 if (0 < nSecBiasedRegions) {
241 for (G4int i=0; i<nSecBiasedRegions; ++i) {
242 if (reg == secBiasedRegions[i]) {
243 secBiasedWeight[i] = w;
244 nBremSplitting[i] = nsplit;
245 secBiasedEnegryLimit[i] = energyLimit;
246 return;
247 }
248 }
249 }
250 /*
251 G4cout << "### G4EmBiasingManager::ActivateSecondaryBiasing: "
252 << " nsplit= " << nsplit << " for the G4Region <"
253 << rname << ">" << G4endl;
254 */
255
256 // new region
257 secBiasedRegions.push_back(reg);
258 secBiasedWeight.push_back(w);
259 nBremSplitting.push_back(nsplit);
260 secBiasedEnegryLimit.push_back(energyLimit);
262 //G4cout << "nSecBiasedRegions= " << nSecBiasedRegions << G4endl;
263}
double G4double
Definition: G4Types.hh:83
std::vector< G4double > secBiasedEnegryLimit
std::vector< G4double > secBiasedWeight
std::vector< const G4Region * > secBiasedRegions
std::vector< G4int > nBremSplitting
int G4lrint(double ad)
Definition: templates.hh:134

References G4cout, G4endl, G4lrint(), G4RegionStore::GetInstance(), G4RegionStore::GetRegion(), G4InuclParticleNames::name(), nBremSplitting, nSecBiasedRegions, reg, secBiasedEnegryLimit, secBiasedRegions, and secBiasedWeight.

Referenced by G4VEmProcess::ActivateSecondaryBiasing(), and G4VEnergyLossProcess::ActivateSecondaryBiasing().

◆ ApplyDirectionalSplitting() [1/2]

G4double G4EmBiasingManager::ApplyDirectionalSplitting ( std::vector< G4DynamicParticle * > &  vd,
const G4Track track,
G4VEmModel currentModel,
G4int  index,
G4double  tcut 
)
private

Definition at line 643 of file G4EmBiasingManager.cc.

649{
650 // primary is not a gamma. Do nothing with primary
651
652 G4double weight = 1.0;
653 G4double w = secBiasedWeight[index];
654
656 if(1.0 <= w) {
657 fDirectionalSplittingWeights.push_back(weight);
658 return weight;
659 }
660
661 G4double trackWeight = track.GetWeight();
662 G4int nsplit = nBremSplitting[index];
663
664 // double splitting is suppressed
665 if(1 < nsplit && trackWeight>w) {
666
667 weight = w;
668 const G4ThreeVector pos = track.GetPosition();
669
670 tmpSecondaries = vd;
671 vd.clear();
672 vd.reserve(nsplit);
673 for (G4int k=0; k<nsplit; ++k) {
674 if (k>0) {
675 tmpSecondaries.clear();
676 currentModel->SampleSecondaries(&tmpSecondaries,
677 track.GetMaterialCutsCouple(),
678 track.GetDynamicParticle(), tcut);
679 }
680 //for (auto sec : tmpSecondaries) {
681 for (size_t kk=0; kk < tmpSecondaries.size(); ++kk) {
682 if (CheckDirection(pos, tmpSecondaries[kk]->GetMomentumDirection())) {
683 vd.push_back(tmpSecondaries[kk]);
684 fDirectionalSplittingWeights.push_back(1.);
685 } else if (G4UniformRand()<w) {
686 vd.push_back(tmpSecondaries[kk]);
687 fDirectionalSplittingWeights.push_back(1./weight);
688 } else {
689 delete tmpSecondaries[kk];
690 tmpSecondaries[kk] = nullptr;
691 }
692 }
693 } // end of loop over nsplit
694 } else { // no splitting was done; still need weights
695 for (size_t i = 0; i < vd.size(); ++i) {
696 fDirectionalSplittingWeights.push_back(1.0);
697 }
698 }
699 return weight;
700}
static const G4double pos
#define G4UniformRand()
Definition: Randomize.hh:52
std::vector< G4DynamicParticle * > tmpSecondaries
std::vector< G4double > fDirectionalSplittingWeights
G4bool CheckDirection(G4ThreeVector pos, G4ThreeVector momdir) const
G4double GetWeight() const
const G4ThreeVector & GetPosition() const
const G4DynamicParticle * GetDynamicParticle() const
const G4MaterialCutsCouple * GetMaterialCutsCouple() const
virtual void SampleSecondaries(std::vector< G4DynamicParticle * > *, const G4MaterialCutsCouple *, const G4DynamicParticle *, G4double tmin=0.0, G4double tmax=DBL_MAX)=0

References CheckDirection(), fDirectionalSplittingWeights, G4UniformRand, G4Track::GetDynamicParticle(), G4Track::GetMaterialCutsCouple(), G4Track::GetPosition(), G4Track::GetWeight(), nBremSplitting, pos, G4VEmModel::SampleSecondaries(), secBiasedWeight, and tmpSecondaries.

◆ ApplyDirectionalSplitting() [2/2]

G4double G4EmBiasingManager::ApplyDirectionalSplitting ( std::vector< G4DynamicParticle * > &  vd,
const G4Track track,
G4VEmModel currentModel,
G4int  index,
G4double  tcut,
G4ParticleChangeForGamma partChange 
)
private

Definition at line 514 of file G4EmBiasingManager.cc.

521{
522 // primary is gamma. do splitting/RR as appropriate
523 // method applied for any number of secondaries
524
525 G4double weight = 1.0;
526 G4double w = secBiasedWeight[index];
527
529 if(1.0 <= w) {
530 fDirectionalSplittingWeights.push_back(weight);
531 return weight;
532 }
533
534 G4double trackWeight = track.GetWeight();
535 G4int nsplit = nBremSplitting[index];
536
537 // double splitting is suppressed
538 if(1 < nsplit && trackWeight>w) {
539
540 weight = w;
541 const G4ThreeVector pos = track.GetPosition();
542
543 G4bool foundPrimaryParticle = false;
544 G4double primaryEnergy = 0.;
545 G4ThreeVector primaryMomdir(0.,0.,0.);
546 G4double primaryWeight = trackWeight;
547
548 tmpSecondaries = vd;
549 vd.clear();
550 vd.reserve(nsplit);
551 for (G4int k=0; k<nsplit; ++k) {
552 if (k>0) { // for k==0, SampleSecondaries has already been called
553 tmpSecondaries.clear();
554 // SampleSecondaries modifies primary info stored in partChange
555 currentModel->SampleSecondaries(&tmpSecondaries,
556 track.GetMaterialCutsCouple(),
557 track.GetDynamicParticle(), tcut);
558 }
559 for (size_t kk=0; kk<tmpSecondaries.size(); ++kk) {
560 if (tmpSecondaries[kk]->GetParticleDefinition() == theGamma) {
561 if (CheckDirection(pos, tmpSecondaries[kk]->GetMomentumDirection())){
562 vd.push_back(tmpSecondaries[kk]);
563 fDirectionalSplittingWeights.push_back(1.);
564 } else if (G4UniformRand() < w) {
565 vd.push_back(tmpSecondaries[kk]);
566 fDirectionalSplittingWeights.push_back(1./weight);
567 } else {
568 delete tmpSecondaries[kk];
569 tmpSecondaries[kk] = nullptr;
570 }
571 } else if (k==0) { // keep charged 2ry from first splitting
572 vd.push_back(tmpSecondaries[kk]);
573 fDirectionalSplittingWeights.push_back(1./weight);
574 } else {
575 delete tmpSecondaries[kk];
576 tmpSecondaries[kk] = nullptr;
577 }
578 }
579
580 // primary
581 G4double en = partChange->GetProposedKineticEnergy();
582 if (en>0.) { // don't add if kinetic energy = 0
583 G4ThreeVector momdir = partChange->GetProposedMomentumDirection();
584 if (CheckDirection(pos,momdir)) {
585 // keep only one primary; others are secondaries
586 if (!foundPrimaryParticle) {
587 primaryEnergy = en;
588 primaryMomdir = momdir;
589 foundPrimaryParticle = true;
590 primaryWeight = weight;
591 } else {
593 partChange->GetProposedMomentumDirection(),
594 partChange->GetProposedKineticEnergy());
595 vd.push_back(dp);
596 fDirectionalSplittingWeights.push_back(1.);
597 }
598 } else if (G4UniformRand()<w) { // not going to target. play RR.
599 if (!foundPrimaryParticle) {
600 foundPrimaryParticle = true;
601 primaryEnergy = en;
602 primaryMomdir = momdir;
603 primaryWeight = 1.;
604 } else {
606 partChange->GetProposedMomentumDirection(),
607 partChange->GetProposedKineticEnergy());
608 vd.push_back(dp);
609 fDirectionalSplittingWeights.push_back(1./weight);
610 }
611 }
612 }
613 } // end of loop over nsplit
614
615 partChange->ProposeWeight(primaryWeight);
616 partChange->SetProposedKineticEnergy(primaryEnergy);
617 partChange->ProposeMomentumDirection(primaryMomdir);
618 } else {
619 for (size_t i = 0; i < vd.size(); ++i) {
620 fDirectionalSplittingWeights.push_back(1.);
621 }
622 }
623
624 return weight;
625}
bool G4bool
Definition: G4Types.hh:86
void SetProposedKineticEnergy(G4double proposedKinEnergy)
void ProposeMomentumDirection(G4double Px, G4double Py, G4double Pz)
const G4ThreeVector & GetProposedMomentumDirection() const
void ProposeWeight(G4double finalWeight)

References CheckDirection(), fDirectionalSplittingWeights, G4UniformRand, G4Track::GetDynamicParticle(), G4Track::GetMaterialCutsCouple(), G4Track::GetPosition(), G4ParticleChangeForGamma::GetProposedKineticEnergy(), G4ParticleChangeForGamma::GetProposedMomentumDirection(), G4Track::GetWeight(), nBremSplitting, pos, G4ParticleChangeForGamma::ProposeMomentumDirection(), G4VParticleChange::ProposeWeight(), G4VEmModel::SampleSecondaries(), secBiasedWeight, G4ParticleChangeForGamma::SetProposedKineticEnergy(), theGamma, and tmpSecondaries.

Referenced by ApplySecondaryBiasing().

◆ ApplyRangeCut()

void G4EmBiasingManager::ApplyRangeCut ( std::vector< G4DynamicParticle * > &  vd,
const G4Track track,
G4double eloss,
G4double  safety 
)
private

Definition at line 430 of file G4EmBiasingManager.cc.

433{
434 size_t n = vd.size();
435 if(!eIonisation) {
436 eIonisation =
438 }
439 if(eIonisation) {
440 for(size_t k=0; k<n; ++k) {
441 const G4DynamicParticle* dp = vd[k];
442 if(dp->GetDefinition() == theElectron) {
443 G4double e = dp->GetKineticEnergy();
444 if(eIonisation->GetRange(e, track.GetMaterialCutsCouple()) < safety) {
445 eloss += e;
446 delete dp;
447 vd[k] = 0;
448 }
449 }
450 }
451 }
452}
G4ParticleDefinition * GetDefinition() const
G4double GetKineticEnergy() const
G4VEnergyLossProcess * eIonisation
static G4LossTableManager * Instance()
G4VEnergyLossProcess * GetEnergyLossProcess(const G4ParticleDefinition *)
G4double GetRange(G4double kineticEnergy, const G4MaterialCutsCouple *)

References eIonisation, G4DynamicParticle::GetDefinition(), G4LossTableManager::GetEnergyLossProcess(), G4DynamicParticle::GetKineticEnergy(), G4Track::GetMaterialCutsCouple(), G4VEnergyLossProcess::GetRange(), G4LossTableManager::Instance(), CLHEP::detail::n, and theElectron.

Referenced by ApplySecondaryBiasing().

◆ ApplyRussianRoulette()

G4double G4EmBiasingManager::ApplyRussianRoulette ( std::vector< G4DynamicParticle * > &  vd,
G4int  index 
)
inlineprivate

Definition at line 226 of file G4EmBiasingManager.hh.

228{
229 size_t n = vd.size();
230 G4double weight = secBiasedWeight[index];
231 for(size_t k=0; k<n; ++k) {
232 if(G4UniformRand()*weight > 1.0) {
233 const G4DynamicParticle* dp = vd[k];
234 delete dp;
235 vd[k] = nullptr;
236 }
237 }
238 return weight;
239}

References G4UniformRand, CLHEP::detail::n, and secBiasedWeight.

Referenced by ApplySecondaryBiasing().

◆ ApplySecondaryBiasing() [1/3]

G4double G4EmBiasingManager::ApplySecondaryBiasing ( std::vector< G4DynamicParticle * > &  vd,
const G4Track track,
G4VEmModel currentModel,
G4ParticleChangeForGamma pParticleChange,
G4double eloss,
G4int  coupleIdx,
G4double  tcut,
G4double  safety = 0.0 
)

Definition at line 342 of file G4EmBiasingManager.cc.

351{
352 G4int index = idxSecBiasedCouple[coupleIdx];
353 G4double weight = 1.;
354 if(0 <= index) {
355 size_t n = vd.size();
356
357 // the check cannot be applied per secondary particle
358 // because weight correction is common, so the first
359 // secondary is checked
360 if((0 < n && vd[0]->GetKineticEnergy() < secBiasedEnegryLimit[index])
362
363 G4int nsplit = nBremSplitting[index];
364
365 // Range cut
366 if(0 == nsplit) {
367 if(safety > fSafetyMin) { ApplyRangeCut(vd, track, eloss, safety); }
368
369 // Russian Roulette
370 } else if(1 == nsplit) {
371 weight = ApplyRussianRoulette(vd, index);
372
373 // Splitting
374 } else {
376 weight = ApplyDirectionalSplitting(vd, track, currentModel,
377 index, tcut, pPartChange);
378 } else {
379 G4double tmpEnergy = pPartChange->GetProposedKineticEnergy();
380 G4ThreeVector tmpMomDir = pPartChange->GetProposedMomentumDirection();
381
382 weight = ApplySplitting(vd, track, currentModel, index, tcut);
383
384 pPartChange->SetProposedKineticEnergy(tmpEnergy);
385 pPartChange->ProposeMomentumDirection(tmpMomDir);
386 }
387 }
388 }
389 }
390 return weight;
391}
G4double ApplySplitting(std::vector< G4DynamicParticle * > &vd, const G4Track &track, G4VEmModel *currentModel, G4int index, G4double tcut)
void ApplyRangeCut(std::vector< G4DynamicParticle * > &vd, const G4Track &track, G4double &eloss, G4double safety)
std::vector< G4int > idxSecBiasedCouple
G4double ApplyDirectionalSplitting(std::vector< G4DynamicParticle * > &vd, const G4Track &track, G4VEmModel *currentModel, G4int index, G4double tcut, G4ParticleChangeForGamma *partChange)
G4double ApplyRussianRoulette(std::vector< G4DynamicParticle * > &vd, G4int index)

References ApplyDirectionalSplitting(), ApplyRangeCut(), ApplyRussianRoulette(), ApplySplitting(), fDirectionalSplitting, fSafetyMin, G4ParticleChangeForGamma::GetProposedKineticEnergy(), G4ParticleChangeForGamma::GetProposedMomentumDirection(), idxSecBiasedCouple, CLHEP::detail::n, nBremSplitting, G4ParticleChangeForGamma::ProposeMomentumDirection(), secBiasedEnegryLimit, and G4ParticleChangeForGamma::SetProposedKineticEnergy().

Referenced by G4eplusAnnihilation::AtRestDoIt(), G4VEnergyLossProcess::FillSecondariesAlongStep(), G4VEmProcess::PostStepDoIt(), and G4VEnergyLossProcess::PostStepDoIt().

◆ ApplySecondaryBiasing() [2/3]

G4double G4EmBiasingManager::ApplySecondaryBiasing ( std::vector< G4DynamicParticle * > &  vd,
const G4Track track,
G4VEmModel currentModel,
G4ParticleChangeForLoss pParticleChange,
G4double eloss,
G4int  coupleIdx,
G4double  tcut,
G4double  safety = 0.0 
)

Definition at line 289 of file G4EmBiasingManager.cc.

298{
299 G4int index = idxSecBiasedCouple[coupleIdx];
300 G4double weight = 1.;
301 if(0 <= index) {
302 size_t n = vd.size();
303
304 // the check cannot be applied per secondary particle
305 // because weight correction is common, so the first
306 // secondary is checked
307 if((0 < n && vd[0]->GetKineticEnergy() < secBiasedEnegryLimit[index])
309
310 G4int nsplit = nBremSplitting[index];
311
312 // Range cut
313 if(0 == nsplit) {
314 if(safety > fSafetyMin) { ApplyRangeCut(vd, track, eloss, safety); }
315
316 // Russian Roulette
317 } else if(1 == nsplit) {
318 weight = ApplyRussianRoulette(vd, index);
319
320 // Splitting
321 } else {
323 weight = ApplyDirectionalSplitting(vd, track, currentModel, index, tcut);
324 } else {
325 G4double tmpEnergy = pPartChange->GetProposedKineticEnergy();
326 G4ThreeVector tmpMomDir = pPartChange->GetProposedMomentumDirection();
327
328 weight = ApplySplitting(vd, track, currentModel, index, tcut);
329
330 pPartChange->SetProposedKineticEnergy(tmpEnergy);
331 pPartChange->ProposeMomentumDirection(tmpMomDir);
332 }
333 }
334 }
335 }
336 return weight;
337}

References ApplyDirectionalSplitting(), ApplyRangeCut(), ApplyRussianRoulette(), ApplySplitting(), fDirectionalSplitting, fSafetyMin, G4ParticleChangeForLoss::GetProposedKineticEnergy(), G4ParticleChangeForLoss::GetProposedMomentumDirection(), idxSecBiasedCouple, CLHEP::detail::n, nBremSplitting, G4ParticleChangeForLoss::ProposeMomentumDirection(), secBiasedEnegryLimit, and G4ParticleChangeForLoss::SetProposedKineticEnergy().

◆ ApplySecondaryBiasing() [3/3]

G4double G4EmBiasingManager::ApplySecondaryBiasing ( std::vector< G4Track * > &  track,
G4int  coupleIdx 
)

Definition at line 396 of file G4EmBiasingManager.cc.

398{
399 G4int index = idxSecBiasedCouple[coupleIdx];
400 G4double weight = 1.;
401 if(0 <= index) {
402 size_t n = track.size();
403
404 // the check cannot be applied per secondary particle
405 // because weight correction is common, so the first
406 // secondary is checked
407 if(0 < n && track[0]->GetKineticEnergy() < secBiasedEnegryLimit[index]) {
408
409 G4int nsplit = nBremSplitting[index];
410
411 // Russian Roulette only
412 if(1 == nsplit) {
413 weight = secBiasedWeight[index];
414 for(size_t k=0; k<n; ++k) {
415 if(G4UniformRand()*weight > 1.0) {
416 const G4Track* t = track[k];
417 delete t;
418 track[k] = 0;
419 }
420 }
421 }
422 }
423 }
424 return weight;
425}

References G4UniformRand, idxSecBiasedCouple, CLHEP::detail::n, nBremSplitting, secBiasedEnegryLimit, and secBiasedWeight.

◆ ApplySplitting()

G4double G4EmBiasingManager::ApplySplitting ( std::vector< G4DynamicParticle * > &  vd,
const G4Track track,
G4VEmModel currentModel,
G4int  index,
G4double  tcut 
)
private

Definition at line 471 of file G4EmBiasingManager.cc.

476{
477 // method is applied only if 1 secondary created PostStep
478 // in the case of many secondaries there is a contradiction
479 G4double weight = 1.;
480 size_t n = vd.size();
481 G4double w = secBiasedWeight[index];
482
483 if(1 != n || 1.0 <= w) { return weight; }
484
485 G4double trackWeight = track.GetWeight();
486 const G4DynamicParticle* dynParticle = track.GetDynamicParticle();
487
488 G4int nsplit = nBremSplitting[index];
489
490 // double splitting is suppressed
491 if(1 < nsplit && trackWeight>w) {
492
493 weight = w;
494 if(nsplit > (G4int)tmpSecondaries.size()) {
495 tmpSecondaries.reserve(nsplit);
496 }
497 const G4MaterialCutsCouple* couple = track.GetMaterialCutsCouple();
498 // start from 1, because already one secondary created
499 for(G4int k=1; k<nsplit; ++k) {
500 tmpSecondaries.clear();
501 currentModel->SampleSecondaries(&tmpSecondaries, couple, dynParticle,
502 tcut);
503 for (size_t kk=0; kk<tmpSecondaries.size(); ++kk) {
504 vd.push_back(tmpSecondaries[kk]);
505 }
506 }
507 }
508 return weight;
509}

References G4Track::GetDynamicParticle(), G4Track::GetMaterialCutsCouple(), G4Track::GetWeight(), CLHEP::detail::n, nBremSplitting, G4VEmModel::SampleSecondaries(), secBiasedWeight, and tmpSecondaries.

Referenced by ApplySecondaryBiasing().

◆ CheckDirection()

G4bool G4EmBiasingManager::CheckDirection ( G4ThreeVector  pos,
G4ThreeVector  momdir 
) const

Definition at line 456 of file G4EmBiasingManager.cc.

458{
460 G4double angle = momdir.angle(delta);
461 G4double dist = delta.cross(momdir).mag();
462 if (dist <= fDirectionalSplittingRadius && angle < halfpi) {
463 return true;
464 }
465 return false;
466}
static constexpr double halfpi
Definition: G4SIunits.hh:57
static const G4double angle[DIMMOTT]
Hep3Vector cross(const Hep3Vector &) const
double angle(const Hep3Vector &) const
double mag() const
G4double fDirectionalSplittingRadius

References CLHEP::Hep3Vector::angle(), angle, CLHEP::Hep3Vector::cross(), fDirectionalSplittingRadius, fDirectionalSplittingTarget, halfpi, CLHEP::Hep3Vector::mag(), and pos.

Referenced by ApplyDirectionalSplitting().

◆ ForcedInteractionRegion()

G4bool G4EmBiasingManager::ForcedInteractionRegion ( G4int  coupleIdx)
inline

Definition at line 209 of file G4EmBiasingManager.hh.

210{
211 G4bool res = false;
212 if(nForcedRegions > 0) {
213 if(idxForcedCouple[coupleIdx] >= 0) { res = true; }
214 }
215 return res;
216}
std::vector< G4int > idxForcedCouple

References idxForcedCouple, and nForcedRegions.

Referenced by G4VEmProcess::PostStepDoIt(), G4VEnergyLossProcess::PostStepDoIt(), G4VEmProcess::PostStepGetPhysicalInteractionLength(), and G4VEnergyLossProcess::PostStepGetPhysicalInteractionLength().

◆ GetDirectionalSplitting()

G4bool G4EmBiasingManager::GetDirectionalSplitting ( )
inline

Definition at line 125 of file G4EmBiasingManager.hh.

125{ return fDirectionalSplitting; }

References fDirectionalSplitting.

◆ GetStepLimit()

G4double G4EmBiasingManager::GetStepLimit ( G4int  coupleIdx,
G4double  previousStep 
)

Definition at line 267 of file G4EmBiasingManager.cc.

269{
270 if(startTracking) {
271 startTracking = false;
272 G4int i = idxForcedCouple[coupleIdx];
273 if(i < 0) {
275 } else {
278 }
279 } else {
280 currentStepLimit -= previousStep;
281 }
282 if(currentStepLimit < 0.0) { currentStepLimit = 0.0; }
283 return currentStepLimit;
284}
#define DBL_MAX
Definition: templates.hh:62

References currentStepLimit, DBL_MAX, G4UniformRand, idxForcedCouple, lengthForRegion, and startTracking.

Referenced by G4VEmProcess::PostStepGetPhysicalInteractionLength(), and G4VEnergyLossProcess::PostStepGetPhysicalInteractionLength().

◆ GetWeight()

G4double G4EmBiasingManager::GetWeight ( G4int  i)

Definition at line 629 of file G4EmBiasingManager.cc.

630{
631 // normally return 1. If a directionally split particle survives RR,
632 // return 1./(splitting factor)
633 if (fDirectionalSplittingWeights.size() >= (unsigned int)(i+1) ) {
635 fDirectionalSplittingWeights[i] = 1.; // ensure it's not used again
636 return w;
637 } else {
638 return 1.;
639 }
640}

References fDirectionalSplittingWeights.

Referenced by G4eplusAnnihilation::AtRestDoIt(), G4VEmProcess::PostStepDoIt(), and G4VEnergyLossProcess::PostStepDoIt().

◆ Initialise()

void G4EmBiasingManager::Initialise ( const G4ParticleDefinition part,
const G4String procName,
G4int  verbose 
)

Definition at line 82 of file G4EmBiasingManager.cc.

84{
85 //G4cout << "G4EmBiasingManager::Initialise for "
86 // << part.GetParticleName()
87 // << " and " << procName << G4endl;
88 const G4ProductionCutsTable* theCoupleTable=
90 size_t numOfCouples = theCoupleTable->GetTableSize();
91
92 if(0 < nForcedRegions) { idxForcedCouple.resize(numOfCouples, -1); }
93 if(0 < nSecBiasedRegions) { idxSecBiasedCouple.resize(numOfCouples, -1); }
94
95 // Deexcitation
96 for (size_t j=0; j<numOfCouples; ++j) {
97 const G4MaterialCutsCouple* couple =
98 theCoupleTable->GetMaterialCutsCouple(j);
99 const G4ProductionCuts* pcuts = couple->GetProductionCuts();
100 if(0 < nForcedRegions) {
101 for(G4int i=0; i<nForcedRegions; ++i) {
102 if(forcedRegions[i]) {
103 if(pcuts == forcedRegions[i]->GetProductionCuts()) {
104 idxForcedCouple[j] = i;
105 break;
106 }
107 }
108 }
109 }
110 if(0 < nSecBiasedRegions) {
111 for(G4int i=0; i<nSecBiasedRegions; ++i) {
112 if(secBiasedRegions[i]) {
113 if(pcuts == secBiasedRegions[i]->GetProductionCuts()) {
114 idxSecBiasedCouple[j] = i;
115 break;
116 }
117 }
118 }
119 }
120 }
121
127 }
128
129 if (nForcedRegions > 0 && 0 < verbose) {
130 G4cout << " Forced Interaction is activated for "
131 << part.GetParticleName() << " and "
132 << procName
133 << " inside G4Regions: " << G4endl;
134 for (G4int i=0; i<nForcedRegions; ++i) {
135 const G4Region* r = forcedRegions[i];
136 if(r) { G4cout << " " << r->GetName() << G4endl; }
137 }
138 }
139 if (nSecBiasedRegions > 0 && 0 < verbose) {
140 G4cout << " Secondary biasing is activated for "
141 << part.GetParticleName() << " and "
142 << procName
143 << " inside G4Regions: " << G4endl;
144 for (G4int i=0; i<nSecBiasedRegions; ++i) {
145 const G4Region* r = secBiasedRegions[i];
146 if(r) {
147 G4cout << " " << r->GetName()
148 << " BiasingWeight= " << secBiasedWeight[i] << G4endl;
149 }
150 }
152 G4cout << " Directional splitting activated, with target position: "
154 << " cm; radius: "
156 << "cm." << G4endl;
157 }
158 }
159}
static constexpr double cm
Definition: G4SIunits.hh:99
void SetDirectionalSplittingRadius(G4double r)
void SetDirectionalSplitting(G4bool v)
void SetDirectionalSplittingTarget(G4ThreeVector v)
static G4EmParameters * Instance()
G4double GetDirectionalSplittingRadius()
G4bool GetDirectionalSplitting() const
G4ThreeVector GetDirectionalSplittingTarget() const
G4ProductionCuts * GetProductionCuts() const
const G4String & GetParticleName() const
const G4MaterialCutsCouple * GetMaterialCutsCouple(G4int i) const
std::size_t GetTableSize() const
static G4ProductionCutsTable * GetProductionCutsTable()
const G4String & GetName() const

References cm, fDirectionalSplitting, fDirectionalSplittingRadius, fDirectionalSplittingTarget, forcedRegions, G4cout, G4endl, G4EmParameters::GetDirectionalSplitting(), G4EmParameters::GetDirectionalSplittingRadius(), G4EmParameters::GetDirectionalSplittingTarget(), G4ProductionCutsTable::GetMaterialCutsCouple(), G4Region::GetName(), G4ParticleDefinition::GetParticleName(), G4MaterialCutsCouple::GetProductionCuts(), G4ProductionCutsTable::GetProductionCutsTable(), G4ProductionCutsTable::GetTableSize(), idxForcedCouple, idxSecBiasedCouple, G4EmParameters::Instance(), nForcedRegions, nSecBiasedRegions, secBiasedRegions, secBiasedWeight, SetDirectionalSplitting(), SetDirectionalSplittingRadius(), and SetDirectionalSplittingTarget().

Referenced by G4VEmProcess::PreparePhysicsTable(), and G4VEnergyLossProcess::PreparePhysicsTable().

◆ operator=()

G4EmBiasingManager & G4EmBiasingManager::operator= ( const G4EmBiasingManager right)
delete

◆ ResetForcedInteraction()

void G4EmBiasingManager::ResetForcedInteraction ( )
inline

Definition at line 218 of file G4EmBiasingManager.hh.

219{
220 startTracking = true;
221}

References startTracking.

Referenced by G4VEmProcess::StartTracking(), and G4VEnergyLossProcess::StartTracking().

◆ SecondaryBiasingRegion()

G4bool G4EmBiasingManager::SecondaryBiasingRegion ( G4int  coupleIdx)
inline

Definition at line 200 of file G4EmBiasingManager.hh.

201{
202 G4bool res = false;
203 if(nSecBiasedRegions > 0) {
204 if(idxSecBiasedCouple[coupleIdx] >= 0) { res = true; }
205 }
206 return res;
207}

References idxSecBiasedCouple, and nSecBiasedRegions.

Referenced by G4eplusAnnihilation::AtRestDoIt(), G4VEnergyLossProcess::FillSecondariesAlongStep(), G4VEmProcess::PostStepDoIt(), and G4VEnergyLossProcess::PostStepDoIt().

◆ SetDirectionalSplitting()

void G4EmBiasingManager::SetDirectionalSplitting ( G4bool  v)
inline

Definition at line 126 of file G4EmBiasingManager.hh.

References fDirectionalSplitting.

Referenced by Initialise().

◆ SetDirectionalSplittingRadius()

void G4EmBiasingManager::SetDirectionalSplittingRadius ( G4double  r)
inline

Definition at line 130 of file G4EmBiasingManager.hh.

References fDirectionalSplittingRadius.

Referenced by Initialise().

◆ SetDirectionalSplittingTarget()

void G4EmBiasingManager::SetDirectionalSplittingTarget ( G4ThreeVector  v)
inline

Definition at line 128 of file G4EmBiasingManager.hh.

References fDirectionalSplittingTarget.

Referenced by Initialise().

Field Documentation

◆ currentStepLimit

G4double G4EmBiasingManager::currentStepLimit = 0.0
private

Definition at line 173 of file G4EmBiasingManager.hh.

Referenced by GetStepLimit().

◆ eIonisation

G4VEnergyLossProcess* G4EmBiasingManager::eIonisation = nullptr
private

Definition at line 167 of file G4EmBiasingManager.hh.

Referenced by ApplyRangeCut().

◆ fDirectionalSplitting

G4bool G4EmBiasingManager::fDirectionalSplitting = false
private

◆ fDirectionalSplittingRadius

G4double G4EmBiasingManager::fDirectionalSplittingRadius = 0.0
private

◆ fDirectionalSplittingTarget

G4ThreeVector G4EmBiasingManager::fDirectionalSplittingTarget
private

◆ fDirectionalSplittingWeights

std::vector<G4double> G4EmBiasingManager::fDirectionalSplittingWeights
private

Definition at line 183 of file G4EmBiasingManager.hh.

Referenced by ApplyDirectionalSplitting(), and GetWeight().

◆ forcedRegions

std::vector<const G4Region*> G4EmBiasingManager::forcedRegions
private

Definition at line 189 of file G4EmBiasingManager.hh.

Referenced by ActivateForcedInteraction(), and Initialise().

◆ fSafetyMin

G4double G4EmBiasingManager::fSafetyMin
private

Definition at line 172 of file G4EmBiasingManager.hh.

Referenced by ApplySecondaryBiasing(), and G4EmBiasingManager().

◆ idxForcedCouple

std::vector<G4int> G4EmBiasingManager::idxForcedCouple
private

Definition at line 193 of file G4EmBiasingManager.hh.

Referenced by ForcedInteractionRegion(), GetStepLimit(), and Initialise().

◆ idxSecBiasedCouple

std::vector<G4int> G4EmBiasingManager::idxSecBiasedCouple
private

◆ lengthForRegion

std::vector<G4double> G4EmBiasingManager::lengthForRegion
private

Definition at line 185 of file G4EmBiasingManager.hh.

Referenced by ActivateForcedInteraction(), and GetStepLimit().

◆ nBremSplitting

std::vector<G4int> G4EmBiasingManager::nBremSplitting
private

◆ nForcedRegions

G4int G4EmBiasingManager::nForcedRegions = 0
private

◆ nSecBiasedRegions

G4int G4EmBiasingManager::nSecBiasedRegions = 0
private

◆ secBiasedEnegryLimit

std::vector<G4double> G4EmBiasingManager::secBiasedEnegryLimit
private

Definition at line 187 of file G4EmBiasingManager.hh.

Referenced by ActivateSecondaryBiasing(), and ApplySecondaryBiasing().

◆ secBiasedRegions

std::vector<const G4Region*> G4EmBiasingManager::secBiasedRegions
private

Definition at line 190 of file G4EmBiasingManager.hh.

Referenced by ActivateSecondaryBiasing(), and Initialise().

◆ secBiasedWeight

std::vector<G4double> G4EmBiasingManager::secBiasedWeight
private

◆ startTracking

G4bool G4EmBiasingManager::startTracking = true
private

Definition at line 179 of file G4EmBiasingManager.hh.

Referenced by GetStepLimit(), and ResetForcedInteraction().

◆ theElectron

const G4ParticleDefinition* G4EmBiasingManager::theElectron
private

Definition at line 169 of file G4EmBiasingManager.hh.

Referenced by ApplyRangeCut(), and G4EmBiasingManager().

◆ theGamma

const G4ParticleDefinition* G4EmBiasingManager::theGamma
private

Definition at line 170 of file G4EmBiasingManager.hh.

Referenced by ApplyDirectionalSplitting(), and G4EmBiasingManager().

◆ tmpSecondaries

std::vector<G4DynamicParticle*> G4EmBiasingManager::tmpSecondaries
private

Definition at line 196 of file G4EmBiasingManager.hh.

Referenced by ApplyDirectionalSplitting(), and ApplySplitting().


The documentation for this class was generated from the following files: