Geant4 Cross Reference

Cross-Referencing   Geant4
Geant4/processes/electromagnetic/muons/src/G4MuIonisation.cc

Version: [ ReleaseNotes ] [ 1.0 ] [ 1.1 ] [ 2.0 ] [ 3.0 ] [ 3.1 ] [ 3.2 ] [ 4.0 ] [ 4.0.p1 ] [ 4.0.p2 ] [ 4.1 ] [ 4.1.p1 ] [ 5.0 ] [ 5.0.p1 ] [ 5.1 ] [ 5.1.p1 ] [ 5.2 ] [ 5.2.p1 ] [ 5.2.p2 ] [ 6.0 ] [ 6.0.p1 ] [ 6.1 ] [ 6.2 ] [ 6.2.p1 ] [ 6.2.p2 ] [ 7.0 ] [ 7.0.p1 ] [ 7.1 ] [ 7.1.p1 ] [ 8.0 ] [ 8.0.p1 ] [ 8.1 ] [ 8.1.p1 ] [ 8.1.p2 ] [ 8.2 ] [ 8.2.p1 ] [ 8.3 ] [ 8.3.p1 ] [ 8.3.p2 ] [ 9.0 ] [ 9.0.p1 ] [ 9.0.p2 ] [ 9.1 ] [ 9.1.p1 ] [ 9.1.p2 ] [ 9.1.p3 ] [ 9.2 ] [ 9.2.p1 ] [ 9.2.p2 ] [ 9.2.p3 ] [ 9.2.p4 ] [ 9.3 ] [ 9.3.p1 ] [ 9.3.p2 ] [ 9.4 ] [ 9.4.p1 ] [ 9.4.p2 ] [ 9.4.p3 ] [ 9.4.p4 ] [ 9.5 ] [ 9.5.p1 ] [ 9.5.p2 ] [ 9.6 ] [ 9.6.p1 ] [ 9.6.p2 ] [ 9.6.p3 ] [ 9.6.p4 ] [ 10.0 ] [ 10.0.p1 ] [ 10.0.p2 ] [ 10.0.p3 ] [ 10.0.p4 ] [ 10.1 ] [ 10.1.p1 ] [ 10.1.p2 ] [ 10.1.p3 ] [ 10.2 ] [ 10.2.p1 ] [ 10.2.p2 ] [ 10.2.p3 ] [ 10.3 ] [ 10.3.p1 ] [ 10.3.p2 ] [ 10.3.p3 ] [ 10.4 ] [ 10.4.p1 ] [ 10.4.p2 ] [ 10.4.p3 ] [ 10.5 ] [ 10.5.p1 ] [ 10.6 ] [ 10.6.p1 ] [ 10.6.p2 ] [ 10.6.p3 ] [ 10.7 ] [ 10.7.p1 ] [ 10.7.p2 ] [ 10.7.p3 ] [ 10.7.p4 ] [ 11.0 ] [ 11.0.p1 ] [ 11.0.p2 ] [ 11.0.p3, ] [ 11.0.p4 ] [ 11.1 ] [ 11.1.1 ] [ 11.1.2 ] [ 11.1.3 ] [ 11.2 ] [ 11.2.1 ] [ 11.2.2 ] [ 11.3.0 ]

Diff markup

Differences between /processes/electromagnetic/muons/src/G4MuIonisation.cc (Version 11.3.0) and /processes/electromagnetic/muons/src/G4MuIonisation.cc (Version 3.1)


                                                   >>   1 // This code implementation is the intellectual property of
                                                   >>   2 // the GEANT4 collaboration.
  1 //                                                  3 //
  2 // ******************************************* <<   4 // By copying, distributing or modifying the Program (or any work
  3 // * License and Disclaimer                    <<   5 // based on the Program) you indicate your acceptance of this statement,
  4 // *                                           <<   6 // and all its terms.
  5 // * The  Geant4 software  is  copyright of th <<   7 //
  6 // * the Geant4 Collaboration.  It is provided <<   8 // $Id: G4MuIonisation.cc,v 1.12 2001/03/23 07:27:29 urban Exp $
  7 // * conditions of the Geant4 Software License <<   9 // GEANT4 tag $Name: geant4-03-01 $
  8 // * LICENSE and available at  http://cern.ch/ <<  10 //
  9 // * include a list of copyright holders.      <<  11 // 
 10 // *                                           <<  12 // --------------------------------------------------------------
 11 // * Neither the authors of this software syst <<  13 //      GEANT 4 class implementation file
 12 // * institutes,nor the agencies providing fin <<  14 //
 13 // * work  make  any representation or  warran <<  15 //      For information related to this code contact:
 14 // * regarding  this  software system or assum <<  16 //      CERN, CN Division, ASD group
 15 // * use.  Please see the license in the file  <<  17 //      History: first implementation, based on object model of
 16 // * for the full disclaimer and the limitatio <<  18 //      2nd December 1995, G.Cosmo
 17 // *                                           <<  19 //      ------------ G4MuIonisation physics process -------------
 18 // * This  code  implementation is the result  <<  20 //                by Laszlo Urban, September 1997
 19 // * technical work of the GEANT4 collaboratio <<  21 // ------------------------------------------------------------------
 20 // * By using,  copying,  modifying or  distri <<  22 // It is the implementation of the NEW IONISATION PROCESS.
 21 // * any work based  on the software)  you  ag <<  23 // It calculates the ionisation of muons.
 22 // * use  in  resulting  scientific  publicati <<  24 // **************************************************************
 23 // * acceptance of all terms of the Geant4 Sof <<  25 // 08-04-98: remove 'tracking cut' of the ionizing particle, MMa
 24 // ******************************************* <<  26 // 26/10/98: new stuff from R.Kokoulin + cleanup , L.Urban
 25 //                                             <<  27 // 10/02/00  modifications , new e.m. structure, L.Urban
 26 // ------------------------------------------- <<  28 // 23/03/01: R.Kokoulin's correction is commented out, L.Urban
 27 //                                             <<  29 // --------------------------------------------------------------
 28 // GEANT4 Class file                           <<  30  
 29 //                                             << 
 30 //                                             << 
 31 // File name:     G4MuIonisation               << 
 32 //                                             << 
 33 // Author:        Laszlo Urban                 << 
 34 //                                             << 
 35 // Creation date: 30.09.1997                   << 
 36 //                                             << 
 37 // Modifications:                              << 
 38 //                                             << 
 39 // 08-04-98 remove 'tracking cut' of the ioniz << 
 40 // 26-10-98 new stuff from R.Kokoulin + cleanu << 
 41 // 10-02-00 modifications , new e.m. structure << 
 42 // 23-03-01 R.Kokoulin's correction is comment << 
 43 // 29-05-01 V.Ivanchenko minor changes to prov << 
 44 // 10-08-01 new methods Store/Retrieve Physics << 
 45 // 28-08-01 new function ComputeRestrictedMean << 
 46 // 17-09-01 migration of Materials to pure STL << 
 47 // 26-09-01 completion of RetrievePhysicsTable << 
 48 // 29-10-01 all static functions no more inlin << 
 49 // 07-11-01 correction(Tmax+xsection computati << 
 50 // 08-11-01 particleMass becomes a local varia << 
 51 // 10-05-02 V.Ivanchenko update to new design  << 
 52 // 04-12-02 V.Ivanchenko the low energy limit  << 
 53 // 23-12-02 Change interface in order to move  << 
 54 // 26-12-02 Secondary production moved to deri << 
 55 // 13-02-03 SubCutoff regime is assigned to a  << 
 56 // 23-05-03 Define default integral + BohrFluc << 
 57 // 03-06-03 Add SetIntegral method to choose f << 
 58 // 03-06-03 Fix initialisation problem for STD << 
 59 // 04-08-03 Set integral=false to be default ( << 
 60 // 08-08-03 STD substitute standard  (V.Ivanch << 
 61 // 12-11-03 G4EnergyLossSTD -> G4EnergyLossPro << 
 62 // 10-02-04 Calculation of radiative correctio << 
 63 // 27-05-04 Set integral to be a default regim << 
 64 // 17-08-04 Utilise mu+ tables for mu- (V.Ivan << 
 65 // 08-11-04 Migration to new interface of Stor << 
 66 // 08-04-05 Major optimisation of internal int << 
 67 // 12-08-05 SetStepLimits(0.2, 0.1*mm) (mma)   << 
 68 // 02-09-05 SetStepLimits(0.2, 1*mm) (V.Ivantc << 
 69 // 12-08-05 SetStepLimits(0.2, 0.1*mm) + integ << 
 70 // 10-01-06 SetStepLimits -> SetStepFunction ( << 
 71 //                                             << 
 72 // ------------------------------------------- << 
 73 //                                             << 
 74 //....oooOO0OOooo........oooOO0OOooo........oo << 
 75 //....oooOO0OOooo........oooOO0OOooo........oo << 
 76                                                    31 
 77 #include "G4MuIonisation.hh"                       32 #include "G4MuIonisation.hh"
 78 #include "G4PhysicalConstants.hh"              <<  33 #include "G4UnitsTable.hh"
 79 #include "G4SystemOfUnits.hh"                  << 
 80 #include "G4Electron.hh"                       << 
 81 #include "G4BraggModel.hh"                     << 
 82 #include "G4BetheBlochModel.hh"                << 
 83 #include "G4MuBetheBlochModel.hh"              << 
 84 #include "G4EmStandUtil.hh"                    << 
 85 #include "G4ICRU73QOModel.hh"                  << 
 86 #include "G4EmParameters.hh"                   << 
 87                                                    34 
 88 //....oooOO0OOooo........oooOO0OOooo........oo <<  35 #include "G4ios.hh"
 89                                                    36 
 90 G4MuIonisation::G4MuIonisation(const G4String& << 
 91   : G4VEnergyLossProcess(name)                 << 
 92 {                                              << 
 93   SetProcessSubType(fIonisation);              << 
 94   SetSecondaryParticle(G4Electron::Electron()) << 
 95 }                                              << 
 96                                                    37 
 97 //....oooOO0OOooo........oooOO0OOooo........oo <<  38 G4double G4MuIonisation::LowerBoundLambda = 1.*keV ;
                                                   >>  39 G4double G4MuIonisation::UpperBoundLambda = 1000000.*TeV ;
                                                   >>  40 G4int  G4MuIonisation::NbinLambda = 150 ;
 98                                                    41 
 99 G4bool G4MuIonisation::IsApplicable(const G4Pa << 
100 {                                              << 
101   return (p.GetPDGCharge() != 0.0);            << 
102 }                                              << 
103                                                    42 
104 //....oooOO0OOooo........oooOO0OOooo........oo <<  43 // constructor and destructor
                                                   >>  44  
                                                   >>  45 G4MuIonisation::G4MuIonisation(const G4String& processName)
                                                   >>  46    : G4VMuEnergyLoss(processName),
                                                   >>  47      theMeanFreePathTable(NULL)
                                                   >>  48 {  }
105                                                    49 
106 G4double G4MuIonisation::MinPrimaryEnergy(cons <<  50 G4MuIonisation::~G4MuIonisation() 
107             const G4Material*,                 << 
108             G4double cut)                      << 
109 {                                                  51 {
110   G4double x = 0.5*cut/CLHEP::electron_mass_c2 <<  52      if (theMeanFreePathTable) {
111   G4double gam = x*ratio + std::sqrt((1. + x)* <<  53         theMeanFreePathTable->clearAndDestroy();
112   return mass*(gam - 1.0);                     <<  54         delete theMeanFreePathTable;
113 }                                              <<  55      }
114                                                    56 
115 //....oooOO0OOooo........oooOO0OOooo........oo <<  57 }
116                                                    58 
117 void                                           <<  59 void G4MuIonisation::BuildPhysicsTable(const G4ParticleDefinition& aParticleType)
118 G4MuIonisation::InitialiseEnergyLossProcess(co <<  60 //  just call BuildLossTable+BuildLambdaTable
119                                             co << 
120 {                                                  61 {
121   if(!isInitialised) {                         <<  62     // get bining from EnergyLoss
                                                   >>  63     LowestKineticEnergy  = GetLowerBoundEloss() ;
                                                   >>  64     HighestKineticEnergy = GetUpperBoundEloss() ;
                                                   >>  65     TotBin               = GetNbinEloss() ;
                                                   >>  66 
                                                   >>  67   BuildLossTable(aParticleType) ;
                                                   >>  68   G4double Charge = aParticleType.GetPDGCharge();     
                                                   >>  69 
                                                   >>  70   if(Charge>0.)
                                                   >>  71   {
                                                   >>  72     RecorderOfmuplusProcess[CounterOfmuplusProcess] = (*this).theLossTable ;
                                                   >>  73     CounterOfmuplusProcess++;
                                                   >>  74   }
                                                   >>  75   else
                                                   >>  76   {
                                                   >>  77     RecorderOfmuminusProcess[CounterOfmuminusProcess] = (*this).theLossTable ;
                                                   >>  78     CounterOfmuminusProcess++;
                                                   >>  79   }
                                                   >>  80  
                                                   >>  81   G4double electronCutInRange = G4Electron::Electron()->GetCuts();  
                                                   >>  82   if(electronCutInRange != lastelectronCutInRange)
                                                   >>  83     BuildLambdaTable(aParticleType) ;
                                                   >>  84  
                                                   >>  85    G4VMuEnergyLoss::BuildDEDXTable(aParticleType) ;
122                                                    86 
123     theParticle = part;                        <<  87   if(&aParticleType == theMuonPlus)  
124     theBaseParticle = bpart;                   <<  88      PrintInfoDefinition() ;
                                                   >>  89 }
125                                                    90 
126     mass = theParticle->GetPDGMass();          <<  91 void G4MuIonisation::BuildLossTable(const G4ParticleDefinition& aParticleType)
127     ratio = CLHEP::electron_mass_c2/mass;      <<  92 {
128     G4double q = theParticle->GetPDGCharge();  <<  93   DeltaCutInKineticEnergy = theElectron->GetCutsInEnergy() ;
129                                                    94 
130     G4EmParameters* param = G4EmParameters::In <<  95   G4double LowEdgeEnergy , ionloss ;
131     G4double elow = 0.2*CLHEP::MeV;            <<  96   G4double deltaloss ;
132     G4double emax = param->MaxKinEnergy();     <<  97   G4double RateMass ;
                                                   >>  98   G4bool isOutRange ;
                                                   >>  99   static const G4MaterialTable* theMaterialTable=
                                                   >> 100                                    G4Material::GetMaterialTable();
                                                   >> 101   const G4double twoln10 = 2.*log(10.) ;
                                                   >> 102   const G4double Factor = twopi_mc2_rcl2 ;
                                                   >> 103   const G4double bg2lim = 0.0169 , taulim = 8.4146e-3 ;
                                                   >> 104 
                                                   >> 105   ParticleMass = aParticleType.GetPDGMass() ;
                                                   >> 106   RateMass = electron_mass_c2/ParticleMass ;
                                                   >> 107 
                                                   >> 108   G4int numOfMaterials = theMaterialTable->length();
                                                   >> 109 
                                                   >> 110   if ( theLossTable) {
                                                   >> 111      theLossTable->clearAndDestroy();
                                                   >> 112      delete theLossTable;
                                                   >> 113   }
                                                   >> 114   theLossTable = new G4PhysicsTable(numOfMaterials);
133                                                   115 
134     // Bragg peak model                        << 116   for (G4int J=0; J<numOfMaterials; J++)
135     if (nullptr == EmModel(0)) {               << 117   {
136       if(q > 0.0) { SetEmModel(new G4BraggMode << 118     G4PhysicsLogVector* aVector = new G4PhysicsLogVector(
137       else        { SetEmModel(new G4ICRU73QOM << 119                     LowestKineticEnergy, HighestKineticEnergy, TotBin);
                                                   >> 120   
                                                   >> 121     G4double ElectronDensity,Eexc,Eexc2,Cden,Mden,Aden,X0den,X1den,taul ;
                                                   >> 122     G4double* ShellCorrectionVector;
                                                   >> 123    
                                                   >> 124     const G4Material* material= (*theMaterialTable)[J];
                                                   >> 125 
                                                   >> 126     ElectronDensity = material->GetElectronDensity();
                                                   >> 127     Eexc = material->GetIonisation()->GetMeanExcitationEnergy();
                                                   >> 128     Eexc2 = Eexc*Eexc ;
                                                   >> 129     Cden = material->GetIonisation()->GetCdensity();
                                                   >> 130     Mden = material->GetIonisation()->GetMdensity();
                                                   >> 131     Aden = material->GetIonisation()->GetAdensity();
                                                   >> 132     X0den = material->GetIonisation()->GetX0density();
                                                   >> 133     X1den = material->GetIonisation()->GetX1density();
                                                   >> 134     taul = material->GetIonisation()->GetTaul() ;
                                                   >> 135     ShellCorrectionVector = material->GetIonisation()
                                                   >> 136                                     ->GetShellCorrectionVector();
                                                   >> 137 
                                                   >> 138     const G4ElementVector* theElementVector=
                                                   >> 139                    material->GetElementVector() ;
                                                   >> 140     const G4double* theAtomicNumDensityVector=
                                                   >> 141                    material->GetAtomicNumDensityVector() ;
                                                   >> 142     const G4int NumberOfElements=
                                                   >> 143                    material->GetNumberOfElements() ;
                                                   >> 144     DeltaCutInKineticEnergyNow = DeltaCutInKineticEnergy[J] ;
                                                   >> 145 
                                                   >> 146     G4double tau,tau0,Tmax,gamma,bg2,beta2,rcut,delta,x,sh ;
                                                   >> 147     for (G4int i = 0 ; i < TotBin ; i++)
                                                   >> 148     {
                                                   >> 149       LowEdgeEnergy = aVector->GetLowEdgeEnergy(i) ;
                                                   >> 150       tau = LowEdgeEnergy/ParticleMass ;
                                                   >> 151       gamma = tau +1. ;
                                                   >> 152       bg2 = tau*(tau+2.) ;
                                                   >> 153       beta2 = bg2/(gamma*gamma) ;
                                                   >> 154       Tmax = 2.*electron_mass_c2*bg2
                                                   >> 155              /(1.+2.*gamma*RateMass+RateMass*RateMass) ;
                                                   >> 156 
                                                   >> 157       if ( tau < taul )
                                                   >> 158       //  low energy part , parametrized energy loss formulae
                                                   >> 159       {
                                                   >> 160         ionloss = 0. ;
                                                   >> 161         deltaloss = 0. ;
                                                   >> 162 
                                                   >> 163         for (G4int iel=0; iel<NumberOfElements; iel++)
                                                   >> 164         {
                                                   >> 165           const G4Element* element = (*theElementVector)(iel);
                                                   >> 166           
                                                   >> 167           if ( tau < element->GetIonisation()->GetTau0())  
                                                   >> 168             ionloss += theAtomicNumDensityVector[iel]
                                                   >> 169                        *( element->GetIonisation()->GetAlow()*sqrt(tau)
                                                   >> 170                        +element->GetIonisation()->GetBlow()*tau) ;
                                                   >> 171           else
                                                   >> 172             ionloss += theAtomicNumDensityVector[iel]
                                                   >> 173                        *  element->GetIonisation()->GetClow()/sqrt(tau) ;
                                                   >> 174         }
                                                   >> 175         if ( DeltaCutInKineticEnergyNow < Tmax)
                                                   >> 176         {
                                                   >> 177           deltaloss = log(Tmax/DeltaCutInKineticEnergyNow)-
                                                   >> 178                       beta2*(1.-DeltaCutInKineticEnergyNow/Tmax) ;
                                                   >> 179           if(aParticleType.GetPDGSpin() == 0.5)
                                                   >> 180             deltaloss += 0.25*(Tmax-DeltaCutInKineticEnergyNow)*
                                                   >> 181                               (Tmax-DeltaCutInKineticEnergyNow)/
                                                   >> 182                         (LowEdgeEnergy*LowEdgeEnergy+proton_mass_c2*proton_mass_c2) ;
                                                   >> 183             deltaloss *= Factor*ElectronDensity/beta2 ;
                                                   >> 184         }
                                                   >> 185         ionloss -= deltaloss ;
                                                   >> 186       }
                                                   >> 187       else
                                                   >> 188       // high energy part , Bethe-Bloch formula 
                                                   >> 189       {
                                                   >> 190 
                                                   >> 191         if ( DeltaCutInKineticEnergyNow < Tmax)
                                                   >> 192           rcut = DeltaCutInKineticEnergyNow/Tmax ;
                                                   >> 193         else
                                                   >> 194           rcut = 1.;
                                                   >> 195 
                                                   >> 196         ionloss = log(2.*electron_mass_c2*bg2*Tmax/Eexc2)
                                                   >> 197                   +log(rcut)-(1.+rcut)*beta2 ;
                                                   >> 198 
                                                   >> 199         // density correction 
                                                   >> 200         x = log(bg2)/twoln10 ;
                                                   >> 201         if ( x < X0den )
                                                   >> 202           delta = 0. ;
                                                   >> 203         else 
                                                   >> 204         {
                                                   >> 205           delta = twoln10*x - Cden ;
                                                   >> 206           if ( x < X1den )
                                                   >> 207             delta += Aden*pow((X1den-x),Mden) ;
                                                   >> 208         } 
                                                   >> 209 
                                                   >> 210         // shell correction 
                                                   >> 211         if ( bg2 > bg2lim ) {
                                                   >> 212           sh = 0. ;      
                                                   >> 213           x = 1. ;
                                                   >> 214           for (G4int k=0; k<=2; k++) {
                                                   >> 215             x *= bg2 ;
                                                   >> 216             sh += ShellCorrectionVector[k]/x;
                                                   >> 217           }
                                                   >> 218         }
                                                   >> 219         else {
                                                   >> 220           sh = 0. ;      
                                                   >> 221           x = 1. ;
                                                   >> 222           for (G4int k=0; k<=2; k++) {
                                                   >> 223              x *= bg2lim ;
                                                   >> 224              sh += ShellCorrectionVector[k]/x;
                                                   >> 225           }
                                                   >> 226           sh *= log(tau/taul)/log(taulim/taul) ;     
                                                   >> 227         }
                                                   >> 228 
                                                   >> 229         ionloss -= delta + sh ;
                                                   >> 230         ionloss /= beta2 ;
                                                   >> 231          
                                                   >> 232       // correction of R. Kokoulin  // has been taken out *************** 
                                                   >> 233       //  G4double E = LowEdgeEnergy+ParticleMass ;
                                                   >> 234       //  G4double epmax = RateMass*E*E/(RateMass*E+ParticleMass) ;
                                                   >> 235       //  G4double apar = log(2.*epmax/electron_mass_c2) ;
                                                   >> 236       //  ionloss += fine_structure_const*(log(2.*E/ParticleMass)-apar/3.)*
                                                   >> 237       //                                  apar*apar/twopi ; 
                                                   >> 238 
                                                   >> 239         ionloss *= Factor*ElectronDensity ;
                                                   >> 240       }
                                                   >> 241       if ( ionloss <= 0.)
                                                   >> 242         ionloss = 0. ;
                                                   >> 243       aVector->PutValue(i,ionloss) ;
138     }                                             244     }
139     EmModel(0)->SetLowEnergyLimit(param->MinKi << 245     theLossTable->insert(aVector);
140     EmModel(0)->SetHighEnergyLimit(elow);      << 246   }
                                                   >> 247 }
141                                                   248 
142     // fluctuation model                       << 249 void G4MuIonisation::BuildLambdaTable(const G4ParticleDefinition& aParticleType)
143     if (nullptr == FluctModel()) {             << 250 {
144       SetFluctModel(G4EmStandUtil::ModelOfFluc << 251   // Build mean free path tables for the delta ray production process
                                                   >> 252   G4double LowEdgeEnergy,Tmax , Value ,sigma ;
                                                   >> 253   G4bool isOutRange ;
                                                   >> 254   const G4MaterialTable* theMaterialTable=G4Material::GetMaterialTable();
                                                   >> 255 
                                                   >> 256   G4int numOfMaterials = theMaterialTable->length();
                                                   >> 257 
                                                   >> 258   if (theMeanFreePathTable) {
                                                   >> 259       theMeanFreePathTable->clearAndDestroy();
                                                   >> 260       delete theMeanFreePathTable;
                                                   >> 261      }
                                                   >> 262 
                                                   >> 263   theMeanFreePathTable = new G4PhysicsTable(numOfMaterials);
                                                   >> 264 
                                                   >> 265   // get electron and particle cuts in kinetic energy
                                                   >> 266   DeltaCutInKineticEnergy = theElectron->GetCutsInEnergy() ;
                                                   >> 267 
                                                   >> 268   for (G4int J=0 ; J < numOfMaterials; J++)
                                                   >> 269   { 
                                                   >> 270     G4PhysicsLogVector* aVector = new G4PhysicsLogVector(
                                                   >> 271                LowerBoundLambda,UpperBoundLambda,NbinLambda);
                                                   >> 272 
                                                   >> 273     const G4Material* material= (*theMaterialTable)[J];
                                                   >> 274     const G4ElementVector* theElementVector=
                                                   >> 275                          material->GetElementVector() ;
                                                   >> 276     const G4double* theAtomicNumDensityVector =
                                                   >> 277                          material->GetAtomicNumDensityVector();
                                                   >> 278     const G4int NumberOfElements=
                                                   >> 279                          material->GetNumberOfElements() ;
                                                   >> 280     DeltaCutInKineticEnergyNow = DeltaCutInKineticEnergy[J] ;
                                                   >> 281 
                                                   >> 282     for ( G4int i = 0 ; i < NbinLambda ; i++ )
                                                   >> 283     {
                                                   >> 284       LowEdgeEnergy = aVector->GetLowEdgeEnergy(i) ;
                                                   >> 285       sigma = 0. ;
                                                   >> 286 
                                                   >> 287       // check threshold here !
                                                   >> 288       G4double Tmax = 2.*electron_mass_c2*LowEdgeEnergy*
                                                   >> 289                      (LowEdgeEnergy+2.*ParticleMass)/
                                                   >> 290                      (ParticleMass*ParticleMass+2.*electron_mass_c2*
                                                   >> 291                      (LowEdgeEnergy+ParticleMass)+
                                                   >> 292                        electron_mass_c2*electron_mass_c2) ;
                                                   >> 293 
                                                   >> 294       if(Tmax > DeltaCutInKineticEnergyNow)
                                                   >> 295       {
                                                   >> 296         for (G4int iel=0; iel<NumberOfElements; iel++ )
                                                   >> 297         {
                                                   >> 298           sigma +=  theAtomicNumDensityVector[iel]*
                                                   >> 299                       ComputeMicroscopicCrossSection(aParticleType,
                                                   >> 300                           LowEdgeEnergy,
                                                   >> 301                           (*theElementVector)(iel)->GetZ() ) ;
                                                   >> 302         }
                                                   >> 303       }
                                                   >> 304 
                                                   >> 305       Value = sigma<=0 ? DBL_MAX : 1./sigma ;     
                                                   >> 306 
                                                   >> 307       aVector->PutValue(i, Value) ;
145     }                                             308     }
146     AddEmModel(1, EmModel(0), FluctModel());   << 
147                                                   309 
148     // high energy model                       << 310     theMeanFreePathTable->insert(aVector);
149     if (nullptr == EmModel(1)) { SetEmModel(ne << 311   }
150     EmModel(1)->SetLowEnergyLimit(elow);       << 312 }
151     EmModel(1)->SetHighEnergyLimit(emax);      << 313 
152     AddEmModel(1, EmModel(1), FluctModel());   << 
153                                                   314 
154     isInitialised = true;                      << 315 G4double G4MuIonisation::ComputeMicroscopicCrossSection(
                                                   >> 316                                  const G4ParticleDefinition& aParticleType,
                                                   >> 317                                  G4double KineticEnergy,
                                                   >> 318                                  G4double AtomicNumber)
                                                   >> 319 {
                                                   >> 320   const G4double xgi[] = {0.06943,0.33001,0.66999,0.93057} ;
                                                   >> 321   const G4double wgi[] = {0.17393,0.32607,0.32607,0.17393} ;
                                                   >> 322   const G4double ak1 = 4.6 ;
                                                   >> 323   const G4int k2 = 2 ;
                                                   >> 324   const G4double masspar = 0.5*ParticleMass*ParticleMass/electron_mass_c2 ;
                                                   >> 325   G4double TotalEnergy=KineticEnergy + ParticleMass;
                                                   >> 326   G4double KnockonMaxEnergy = TotalEnergy/(1.+masspar/TotalEnergy) ; 
                                                   >> 327 
                                                   >> 328   G4double TotalCrossSection= 0. ; 
                                                   >> 329 
                                                   >> 330   if( KnockonMaxEnergy > DeltaCutInKineticEnergyNow )
                                                   >> 331   {
                                                   >> 332     G4double aaa = log(DeltaCutInKineticEnergyNow);
                                                   >> 333     G4double bbb = log(KnockonMaxEnergy) ;
                                                   >> 334     G4int kkk = int((bbb-aaa)/ak1)+k2 ;
                                                   >> 335     G4double hhh = (bbb-aaa)/kkk ;
                                                   >> 336     G4double step = exp(hhh) ;
                                                   >> 337     G4double ymax = 1./KnockonMaxEnergy ;
                                                   >> 338       
                                                   >> 339     for (G4int k=0; k<kkk; k++)
                                                   >> 340     {
                                                   >> 341       G4double ymin = ymax ;
                                                   >> 342       ymax = ymin*step ;
                                                   >> 343       G4double hhy = ymax-ymin ;
                                                   >> 344       for (G4int i=0; i<4; i++)
                                                   >> 345       {
                                                   >> 346         G4double y = ymin+hhy*xgi[i];
                                                   >> 347         G4double ep = 1./y ;
                                                   >> 348         TotalCrossSection += ep*ep*wgi[i]*hhy*
                                                   >> 349                              ComputeDMicroscopicCrossSection(
                                                   >> 350                              aParticleType,KineticEnergy,
                                                   >> 351                              AtomicNumber,ep) ;
                                                   >> 352       }
                                                   >> 353     }
155   }                                               354   }
                                                   >> 355   return TotalCrossSection ;
156 }                                                 356 }
                                                   >> 357  
                                                   >> 358 G4double G4MuIonisation::ComputeDMicroscopicCrossSection(
                                                   >> 359                                  const G4ParticleDefinition& ParticleType,
                                                   >> 360                                  G4double KineticEnergy, G4double AtomicNumber,
                                                   >> 361                                  G4double KnockonEnergy)
                                                   >> 362  // Calculates the differential (D) microscopic cross section
                                                   >> 363  //   using the cross section formula of R.P. Kokoulin (10/98)
                                                   >> 364 {
                                                   >> 365   const G4double masspar=0.5*ParticleMass*ParticleMass/electron_mass_c2 ;
                                                   >> 366   const G4double alphaprime = fine_structure_const/twopi ;
                                                   >> 367   G4double TotalEnergy = KineticEnergy + ParticleMass ;
                                                   >> 368   G4double KnockonMaxEnergy = TotalEnergy/(1.+masspar/TotalEnergy) ;
                                                   >> 369 
                                                   >> 370   G4double DCrossSection = 0. ;
                                                   >> 371 
                                                   >> 372   if(KnockonEnergy >=  KnockonMaxEnergy)  return DCrossSection ;
                                                   >> 373 
                                                   >> 374   G4double v = KnockonEnergy/TotalEnergy ;
                                                   >> 375   DCrossSection = twopi_mc2_rcl2*AtomicNumber*
                                                   >> 376                  (1.-KnockonEnergy/KnockonMaxEnergy+0.5*v*v)/
                                                   >> 377                  (KnockonEnergy*KnockonEnergy) ;
                                                   >> 378   G4double a1 = log(1.+2.*KnockonEnergy/electron_mass_c2) ;
                                                   >> 379   G4double a3 = log(4.*TotalEnergy*(TotalEnergy-KnockonEnergy)/
                                                   >> 380                     (ParticleMass*ParticleMass)) ;
                                                   >> 381    DCrossSection *= (1.+alphaprime*a1*(a3-a1)) ; 
157                                                   382 
158 //....oooOO0OOooo........oooOO0OOooo........oo << 383   return DCrossSection ;
                                                   >> 384 }
                                                   >> 385  
                                                   >> 386 G4VParticleChange* G4MuIonisation::PostStepDoIt(
                                                   >> 387                                               const G4Track& trackData,   
                                                   >> 388                                               const G4Step& stepData)         
                                                   >> 389 {
                                                   >> 390   const G4DynamicParticle* aParticle ;
                                                   >> 391   const G4double alphaprime = fine_structure_const/twopi ;
                                                   >> 392   G4Material* aMaterial;
                                                   >> 393   G4double KineticEnergy,TotalEnergy,TotalMomentum,
                                                   >> 394            betasquare,MaxKineticEnergyTransfer,
                                                   >> 395            DeltaKineticEnergy,DeltaTotalMomentum,costheta,sintheta,phi,
                                                   >> 396            dirx,diry,dirz,finalKineticEnergy,finalPx,finalPy,finalPz,
                                                   >> 397            x,xc,te2,grej,Psquare,Esquare,summass,rate,grejc,finalMomentum ;
                                                   >> 398   G4double Charge ;
                                                   >> 399 
                                                   >> 400   aParticleChange.Initialize(trackData) ;
                                                   >> 401   aMaterial = trackData.GetMaterial() ;
                                                   >> 402   aParticle = trackData.GetDynamicParticle() ;
                                                   >> 403   Charge=aParticle->GetDefinition()->GetPDGCharge();
                                                   >> 404   KineticEnergy=aParticle->GetKineticEnergy();
                                                   >> 405   TotalEnergy=KineticEnergy + ParticleMass ;
                                                   >> 406   Psquare=KineticEnergy*(TotalEnergy+ParticleMass) ;
                                                   >> 407   Esquare=TotalEnergy*TotalEnergy ;
                                                   >> 408   summass = ParticleMass + electron_mass_c2 ;    
                                                   >> 409   G4ParticleMomentum ParticleDirection = aParticle->GetMomentumDirection() ;
                                                   >> 410 
                                                   >> 411   DeltaCutInKineticEnergyNow = DeltaCutInKineticEnergy[aMaterial->GetIndex()];
                                                   >> 412 
                                                   >> 413   // some kinematics......................
                                                   >> 414   betasquare=Psquare/Esquare ;
                                                   >> 415   MaxKineticEnergyTransfer = 2.*electron_mass_c2*Psquare
                                                   >> 416                       /(summass*summass+2.*electron_mass_c2*KineticEnergy);
                                                   >> 417 
                                                   >> 418   // sampling kinetic energy of the delta ray 
                                                   >> 419   if( MaxKineticEnergyTransfer <= DeltaCutInKineticEnergyNow )
                                                   >> 420   {
                                                   >> 421     // pathological case (it should not happen ,
                                                   >> 422     return G4VContinuousDiscreteProcess::PostStepDoIt(trackData,stepData);
                                                   >> 423   }
                                                   >> 424   else
                                                   >> 425   {
                                                   >> 426    // normal case ......................................
                                                   >> 427     xc=DeltaCutInKineticEnergyNow/MaxKineticEnergyTransfer ;
                                                   >> 428     rate=MaxKineticEnergyTransfer/TotalEnergy ;
                                                   >> 429     te2=0.5*rate*rate ;
                                                   >> 430 
                                                   >> 431    // sampling follows ...
                                                   >> 432     G4double a0=log(2.*TotalEnergy/ParticleMass) ;
                                                   >> 433     grejc=(1.-betasquare*xc+te2*xc*xc)*
                                                   >> 434             (1.+ alphaprime*a0*a0) ;
                                                   >> 435     do {
                                                   >> 436         x=xc/(1.-(1.-xc)*G4UniformRand());
                                                   >> 437         G4double twoep = 2.*x*MaxKineticEnergyTransfer ;
                                                   >> 438         grej=(1.-x*(betasquare-x*te2))*
                                                   >> 439              (1.+alphaprime*log(1.+twoep/electron_mass_c2)*
                                                   >> 440              (a0+log((2.*TotalEnergy-twoep)/ParticleMass)-
                                                   >> 441               log(1.+twoep/electron_mass_c2)))
                                                   >> 442               /grejc ;
                                                   >> 443        
                                                   >> 444       } while( G4UniformRand()>grej );
                                                   >> 445    }
                                                   >> 446   
                                                   >> 447    DeltaKineticEnergy = x * MaxKineticEnergyTransfer ;
                                                   >> 448 
                                                   >> 449    if(DeltaKineticEnergy <= 0.)
                                                   >> 450      return G4VContinuousDiscreteProcess::PostStepDoIt(trackData,stepData);
                                                   >> 451 
                                                   >> 452    DeltaTotalMomentum = sqrt(DeltaKineticEnergy * (DeltaKineticEnergy +
                                                   >> 453                                                2. * electron_mass_c2 )) ;
                                                   >> 454    TotalMomentum = sqrt(Psquare) ;
                                                   >> 455    costheta = DeltaKineticEnergy * (TotalEnergy + electron_mass_c2)
                                                   >> 456             /(DeltaTotalMomentum * TotalMomentum) ;
                                                   >> 457 
                                                   >> 458    //  protection against costheta > 1 or < -1   ---------------
                                                   >> 459    if ( costheta < -1. ) 
                                                   >> 460           costheta = -1. ;
                                                   >> 461    if ( costheta > +1. ) 
                                                   >> 462           costheta = +1. ;
                                                   >> 463 
                                                   >> 464    //  direction of the delta electron  ........
                                                   >> 465    phi = twopi * G4UniformRand() ; 
                                                   >> 466    sintheta = sqrt((1.+costheta)*(1.-costheta));
                                                   >> 467    dirx = sintheta * cos(phi) ;
                                                   >> 468    diry = sintheta * sin(phi) ;
                                                   >> 469    dirz = costheta ;
                                                   >> 470    G4ThreeVector DeltaDirection(dirx,diry,dirz) ;
                                                   >> 471    DeltaDirection.rotateUz(ParticleDirection) ;
                                                   >> 472 
                                                   >> 473    // create G4DynamicParticle object for delta ray
                                                   >> 474    G4DynamicParticle *theDeltaRay = new G4DynamicParticle;
                                                   >> 475    theDeltaRay->SetKineticEnergy( DeltaKineticEnergy );
                                                   >> 476    theDeltaRay->SetMomentumDirection(
                                                   >> 477                    DeltaDirection.x(),DeltaDirection.y(),DeltaDirection.z());
                                                   >> 478    theDeltaRay->SetDefinition(G4Electron::Electron());
                                                   >> 479    finalKineticEnergy = KineticEnergy - DeltaKineticEnergy ;
                                                   >> 480    if (finalKineticEnergy > 0. )
                                                   >> 481      {
                                                   >> 482       finalPx = TotalMomentum*ParticleDirection.x()
                                                   >> 483                         - DeltaTotalMomentum*DeltaDirection.x();
                                                   >> 484       finalPy = TotalMomentum*ParticleDirection.y()
                                                   >> 485                         - DeltaTotalMomentum*DeltaDirection.y();
                                                   >> 486       finalPz = TotalMomentum*ParticleDirection.z()
                                                   >> 487                         - DeltaTotalMomentum*DeltaDirection.z();
                                                   >> 488       finalMomentum =
                                                   >> 489                 sqrt(finalPx*finalPx+finalPy*finalPy+finalPz*finalPz) ;
                                                   >> 490       finalPx /= finalMomentum ;
                                                   >> 491       finalPy /= finalMomentum ;
                                                   >> 492       finalPz /= finalMomentum ;
                                                   >> 493 
                                                   >> 494       aParticleChange.SetMomentumChange( finalPx,finalPy,finalPz );
                                                   >> 495      }
                                                   >> 496    else
                                                   >> 497      {
                                                   >> 498        finalKineticEnergy = 0. ;
                                                   >> 499        aParticleChange.SetStatusChange(fStopButAlive);
                                                   >> 500      }
                                                   >> 501 
                                                   >> 502    aParticleChange.SetEnergyChange( finalKineticEnergy );
                                                   >> 503    aParticleChange.SetNumberOfSecondaries(1);
                                                   >> 504    aParticleChange.AddSecondary( theDeltaRay );
                                                   >> 505    aParticleChange.SetLocalEnergyDeposit (0.);
                                                   >> 506       
                                                   >> 507    return G4VContinuousDiscreteProcess::PostStepDoIt(trackData,stepData);
                                                   >> 508 }
159                                                   509 
160 void G4MuIonisation::ProcessDescription(std::o << 510 void G4MuIonisation::PrintInfoDefinition()
161 {                                                 511 {
162   out << "  Muon ionisation";                  << 512   G4String comments = "knock-on electron cross sections .\n ";
163   G4VEnergyLossProcess::ProcessDescription(out << 513            comments += "         Good description above the mean excitation energy.\n";
                                                   >> 514            comments += "         delta ray energy sampled from  differential Xsection." ;
                                                   >> 515 
                                                   >> 516   G4cout << G4endl << GetProcessName() << ":  " << comments
                                                   >> 517          << "\n      PhysicsTables from " << G4BestUnit(LowerBoundLambda,
                                                   >> 518                                                "Energy")
                                                   >> 519          << " to " << G4BestUnit(UpperBoundLambda,"Energy")
                                                   >> 520          << " in " << NbinLambda << " bins. \n";
164 }                                                 521 }
165                                                   522 
166 //....oooOO0OOooo........oooOO0OOooo........oo << 
167                                                   523