158const G4int G4IntraNucleiCascader::itry_max = 100;
159const G4int G4IntraNucleiCascader::reflection_cut = 50;
160const G4double G4IntraNucleiCascader::small_ekin = 0.001*MeV;
161const G4double G4IntraNucleiCascader::quasielast_cut = 1*MeV;
170 theCascadeHistory(0), tnuclei(0), bnuclei(0), bparticle(0),
171 minimum_recoil_A(0.), coulombBarrier(0.),
183 delete theElementaryParticleCollider;
184 delete theRecoilMaker;
185 delete theClusterMaker;
186 delete theCascadeHistory;
187 delete nucleusTarget;
193 model->setVerboseLevel(verbose);
194 theElementaryParticleCollider->setVerboseLevel(verbose);
195 theRecoilMaker->setVerboseLevel(verbose);
198 if (theClusterMaker) theClusterMaker->setVerboseLevel(verbose);
199 if (theCascadeHistory) theCascadeHistory->setVerboseLevel(verbose);
219 if (theCascadeHistory) theCascadeHistory->Print(
G4cout);
221 finalize(itry, bullet, target, globalOutput);
232 G4cout <<
" >>> G4IntraNucleiCascader::rescatter " <<
G4endl;
245 if (theCascadeHistory) theCascadeHistory->Print(
G4cout);
247 finalize(itry, bullet, target, globalOutput);
254 G4cout <<
" >>> G4IntraNucleiCascader::initialize " <<
G4endl;
257 theRecoilMaker->setTolerance(small_ekin);
270 if (!bnuclei && !bparticle) {
271 G4cerr <<
" G4IntraNucleiCascader: projectile is not a valid particle."
280 G4cerr <<
" Target is not a nucleus. Abandoning." <<
G4endl;
284 model->generateModel(tnuclei);
285 coulombBarrier = 0.00126*tnuclei->
getZ() / (1.+
G4cbrt(tnuclei->getA()));
289 minimum_recoil_A = 0.;
293 G4cout <<
" intitial momentum E " << momentum_in.
e() <<
" Px "
294 << momentum_in.
x() <<
" Py " << momentum_in.
y() <<
" Pz "
305 G4cout <<
" IntraNucleiCascader itry " << itry <<
" inter_case "
311 new_cascad_particles.clear();
312 theExitonConfiguration.clear();
313 cascad_particles.clear();
315 if (theCascadeHistory) theCascadeHistory->Clear();
323 G4cout <<
" >>> G4IntraNucleiCascader::setupCascade" <<
G4endl;
327 G4cout <<
" bparticle charge " << bparticle->getCharge()
328 <<
" baryon number " << bparticle->baryon() <<
G4endl;
330 cascad_particles.push_back(model->initializeCascad(bparticle));
332 G4int ab = bnuclei->getA();
333 G4int zb = bnuclei->getZ();
336 model->initializeCascad(bnuclei, tnuclei, all_particles);
338 cascad_particles = all_particles.first;
339 output.addOutgoingParticles(all_particles.second);
341 if (cascad_particles.size() == 0) {
344 for (i = 0; i < ab; i++) {
345 G4int knd = i < zb ? 1 : 2;
346 theExitonConfiguration.incrementQP(knd);
352 for (i = 0; i < ihn; i++) theExitonConfiguration.incrementHoles(2);
353 for (i = 0; i < ihz; i++) theExitonConfiguration.incrementHoles(1);
366 while (!cascad_particles.empty() && !model->empty()) {
370 G4cout <<
" Iteration " << iloop <<
": Number of cparticles "
371 << cascad_particles.size() <<
" last one: \n"
372 << cascad_particles.back() <<
G4endl;
376 if (theCascadeHistory) {
377 theCascadeHistory->AddEntry(cascad_particles.back());
379 G4cout <<
" active cparticle got history ID "
380 << cascad_particles.back().getHistoryId() <<
G4endl;
387 G4cout <<
" particle is non-interacting; moving to output" <<
G4endl;
389 output.addOutgoingParticle(cascad_particles.back().getParticle());
390 cascad_particles.pop_back();
395 model->generateParticleFate(cascad_particles.back(),
396 theElementaryParticleCollider,
397 new_cascad_particles);
400 if (theCascadeHistory && new_cascad_particles.size()>1)
401 theCascadeHistory->AddVertex(cascad_particles.back(), new_cascad_particles);
404 G4cout <<
" After generate fate: New particles "
405 << new_cascad_particles.size() <<
G4endl
406 <<
" Discarding last cparticle from list " <<
G4endl;
409 cascad_particles.pop_back();
413 if (new_cascad_particles.size() == 1) {
416 if (model->stillInside(currentCParticle)) {
421 model->worthToPropagate(currentCParticle)) {
423 cascad_particles.push_back(currentCParticle);
439 G4cout <<
" KE " << KE <<
" barrier " << Q*coulombBarrier <<
G4endl;
441 if (KE < Q*coulombBarrier) {
447 if (KE > 0.0001) CBP =
G4Exp(-0.0181*0.5*tnuclei->getZ()*
448 (1./KE - 1./coulombBarrier)*
449 std::sqrt(mass*(coulombBarrier-KE)) );
456 output.addOutgoingParticle(currentParticle);
461 output.addOutgoingParticle(currentParticle);
464 G4cout <<
" Goes out\n" << output.getOutgoingParticles().back()
472 cascad_particles.insert(cascad_particles.end(),
473 new_cascad_particles.begin(),
474 new_cascad_particles.end());
476 std::pair<G4int, G4int> holes = model->getTypesOfNucleonsInvolved();
478 G4cout <<
" adding new exciton holes " << holes.first <<
","
479 << holes.second <<
G4endl;
481 theExitonConfiguration.incrementHoles(holes.first);
483 if (holes.second > 0)
484 theExitonConfiguration.incrementHoles(holes.second);
489 output, cascad_particles);
491 G4double aresid = theRecoilMaker->getRecoilA();
493 G4cout <<
" cparticles remaining " << cascad_particles.size()
494 <<
" nucleus (model) has "
495 << model->getNumberOfNeutrons() <<
" n, "
496 << model->getNumberOfProtons() <<
" p "
497 <<
" residual fragment A " << aresid <<
G4endl;
500 if (aresid <= minimum_recoil_A)
return;
509 G4cout <<
" >>> G4IntraNucleiCascader::finishCascade ?" <<
G4endl;
512 output.addOutgoingParticles(cascad_particles);
513 cascad_particles.clear();
518 output.printCollisionOutput();
522 if (theClusterMaker) {
524 theClusterMaker->FindClusters(output);
532 output.printCollisionOutput();
537 G4int afin = theRecoilMaker->getRecoilA();
538 G4int zfin = theRecoilMaker->getRecoilZ();
543 if (!theRecoilMaker->goodFragment() && !theRecoilMaker->wholeEvent()) {
545 G4cerr <<
" Recoil nucleus is not physical: A=" << afin <<
" Z="
553 G4cout <<
" afin " << afin <<
" zfin " << zfin <<
G4endl;
556 if (afin == 0)
return true;
559 G4int last_type = (zfin==1) ? 1 : 2;
565 if (mres-mass < -small_ekin) {
570 if (mres-mass > small_ekin) {
572 G4cerr <<
" extra energy with recoil nucleon" <<
G4endl;
582 G4cout <<
" adding recoiling nucleon to output list\n"
583 << last_particle <<
G4endl;
586 output.addOutgoingParticle(last_particle);
594 if (output.numberOfOutgoingParticles() == 1) {
595 G4double Eex = theRecoilMaker->getRecoilExcitation();
596 if (std::abs(Eex) < quasielast_cut) {
598 G4cout <<
" quasi-elastic scatter with " << Eex <<
" MeV recoil"
602 theRecoilMaker->setRecoilExcitation(Eex=0.);
604 G4cout <<
" Eex reset to " << theRecoilMaker->getRecoilExcitation()
610 if (theRecoilMaker->goodNucleus()) {
611 theRecoilMaker->addExcitonConfiguration(theExitonConfiguration);
613 G4Fragment* recoilFrag = theRecoilMaker->makeRecoilFragment();
615 G4cerr <<
"Got null pointer for recoil fragment!" <<
G4endl;
620 G4cout <<
" adding recoil fragment to output list" <<
G4endl;
622 output.addRecoilFragment(*recoilFrag);
626 std::vector<G4InuclElementaryParticle>& opart = output.getOutgoingParticles();
630 if (theRecoilMaker->wholeEvent() || theRecoilMaker->goodNucleus()) {
633 output.setVerboseLevel(0);
635 if (output.acceptable())
return true;
640 if (afin <= minimum_recoil_A && minimum_recoil_A < tnuclei->getA()) {
643 G4cout <<
" minimum recoil fragment increased to A " << minimum_recoil_A
659 if (itry >= itry_max) {
661 G4cout <<
" IntraNucleiCascader-> no inelastic interaction after "
662 << itry <<
" attempts " <<
G4endl;
665 output.trivialise(bullet, target);
667 G4cout <<
" IntraNucleiCascader output after trials " << itry <<
G4endl;
671 globalOutput.
add(output);
682 if (theNucleusA > 1) {
684 nucleusTarget->
fill(0., theNucleusA, theNucleusZ, 0.);
685 return nucleusTarget;
701 G4cout <<
" >>> G4IntraNucleiCascader::preloadCascade" <<
G4endl;
709 G4cout <<
" >>> G4IntraNucleiCascader::copyWoundedNucleus" <<
G4endl;
712 theExitonConfiguration.clear();
721 theExitonConfiguration.incrementHoles(nuclType);
728 G4cout <<
" nucleus has " << theExitonConfiguration.neutronHoles
729 <<
" neutrons hit, " << theExitonConfiguration.protonHoles
730 <<
" protons hit" <<
G4endl;
733 model->reset(theExitonConfiguration.neutronHoles,
734 theExitonConfiguration.protonHoles, &hitNucleons);
740 G4cout <<
" >>> G4IntraNucleiCascader::copySecondaries" <<
G4endl;
742 for (
size_t i=0; i<secondaries->size(); i++) {
749 std::sort(cascad_particles.begin(), cascad_particles.end(),
753 G4cout <<
" Original list of " << secondaries->size() <<
" secondaries"
754 <<
" produced " << cascad_particles.size() <<
" cascade, "
755 << output.numberOfOutgoingParticles() <<
" released particles, "
756 << output.numberOfOutgoingNuclei() <<
" fragments" <<
G4endl;
777 G4cout <<
" >>> G4IntraNucleiCascader::processSecondary "
782 cascad_particles.resize(cascad_particles.size()+1);
798 G4cout <<
" Created cascade particle \n" << cpart <<
G4endl;
808 G4cout <<
" >>> G4IntraNucleiCascader::releaseSecondary "
813 if (
dynamic_cast<const G4Ions*
>(kpd)) {
815 output.getOutgoingNuclei().resize(output.numberOfOutgoingNuclei()+1);
821 G4cout <<
" Created pre-cascade fragment\n" << inucl <<
G4endl;
824 output.getOutgoingParticles().resize(output.numberOfOutgoingParticles()+1);
830 G4cout <<
" Created invalid pre-cascade particle\n" << ipart <<
G4endl;
845 theExitonConfiguration.incrementQP(xtype);
846 if (theCascadeHistory) theCascadeHistory->DropEntry(trapped);
852 if (theCascadeHistory) theCascadeHistory->DropEntry(trapped);
859 G4cout <<
" non-standard should be absorbed, now released\n"
863 output.addOutgoingParticle(trappedP);
872 G4cout <<
" unstable must be decayed in flight" <<
G4endl;
879 G4cerr <<
" no decay table! Releasing trapped particle" <<
G4endl;
881 output.addOutgoingParticle(trappedP);
889 G4cerr <<
" no daughters! Releasing trapped particle" <<
G4endl;
891 output.addOutgoingParticle(trappedP);
901 daughters->
Boost(decayEnergy, decayDir);
919 output.addOutgoingParticle(idaugEP);
std::vector< G4InuclElementaryParticle >::iterator particleIterator
G4double G4Exp(G4double initial_x)
Exponential Function double precision.
CLHEP::HepLorentzVector G4LorentzVector
CLHEP::Hep3Vector G4ThreeVector
G4GLOB_DLL std::ostream G4cerr
G4GLOB_DLL std::ostream G4cout
G4int getGeneration() const
void updateZone(G4int izone)
const G4InuclElementaryParticle & getParticle() const
void setGeneration(G4int gen)
void updatePosition(const G4ThreeVector &pos)
void setMovingInsideNuclei(G4bool isMovingIn=true)
G4int getNumberOfReflections() const
void initializePath(G4double npath)
G4int getCurrentZone() const
const G4ThreeVector & getPosition() const
static const G4CascadeChannel * GetTable(G4int initialState)
virtual void setVerboseLevel(G4int verbose=0)
G4CascadeColliderBase(const G4String &name, G4int verbose=0)
G4InteractionCase interCase
static G4bool doCoalescence()
static G4bool showHistory()
void add(const G4CollisionOutput &right)
void Boost(G4double totalEnergy, const G4ThreeVector &momentumDirection)
G4VDecayChannel * SelectADecayChannel(G4double parentMass=-1.)
void processTrappedParticle(const G4CascadParticle &trapped)
void releaseSecondary(const G4KineticTrack *aSecondary)
void copyWoundedNucleus(G4V3DNucleus *theNucleus)
G4bool particleCanInteract(const G4CascadParticle &cpart) const
void rescatter(G4InuclParticle *bullet, G4KineticTrackVector *theSecondaries, G4V3DNucleus *theNucleus, G4CollisionOutput &globalOutput)
void setVerboseLevel(G4int verbose=0)
void decayTrappedParticle(const G4CascadParticle &trapped)
void collide(G4InuclParticle *bullet, G4InuclParticle *target, G4CollisionOutput &globalOutput)
G4bool initialize(G4InuclParticle *bullet, G4InuclParticle *target)
virtual ~G4IntraNucleiCascader()
G4InuclParticle * createTarget(G4V3DNucleus *theNucleus)
void preloadCascade(G4V3DNucleus *theNucleus, G4KineticTrackVector *theSecondaries)
void copySecondaries(G4KineticTrackVector *theSecondaries)
void processSecondary(const G4KineticTrack *aSecondary)
void newCascade(G4int itry)
void finalize(G4int itry, G4InuclParticle *bullet, G4InuclParticle *target, G4CollisionOutput &globalOutput)
void fill(G4int ityp, Model model=DefaultModel)
static G4double getParticleMass(G4int type)
void fill(G4int a, G4int z, G4double exc=0., Model model=DefaultModel)
const G4ParticleDefinition * getDefinition() const
G4double getKineticEnergy() const
G4LorentzVector getMomentum() const
G4double getEnergy() const
G4double getCharge() const
const G4ThreeVector & GetPosition() const
const G4ParticleDefinition * GetDefinition() const
const G4LorentzVector & Get4Momentum() const
std::pair< std::vector< G4CascadParticle >, std::vector< G4InuclElementaryParticle > > modelLists
const G4ThreeVector & GetPosition() const
const G4ParticleDefinition * GetParticleType() const
G4int GetAtomicNumber() const
G4double GetPDGMass() const
G4int GetAtomicMass() const
G4DecayTable * GetDecayTable() const
const G4String & GetParticleName() const
virtual G4Nucleon * GetNextNucleon()=0
virtual G4int GetCharge()=0
virtual G4bool StartLoop()=0
virtual G4int GetMassNumber()=0
virtual G4DecayProducts * DecayIt(G4double parentMass=-1.0)=0
G4double G4cbrt(G4double x)