Geant4 9.6.0
Toolkit for the simulation of the passage of particles through matter
Loading...
Searching...
No Matches
G4QKaonPlusElasticCrossSection.cc
Go to the documentation of this file.
1//
2// ********************************************************************
3// * License and Disclaimer *
4// * *
5// * The Geant4 software is copyright of the Copyright Holders of *
6// * the Geant4 Collaboration. It is provided under the terms and *
7// * conditions of the Geant4 Software License, included in the file *
8// * LICENSE and available at http://cern.ch/geant4/license . These *
9// * include a list of copyright holders. *
10// * *
11// * Neither the authors of this software system, nor their employing *
12// * institutes,nor the agencies providing financial support for this *
13// * work make any representation or warranty, express or implied, *
14// * regarding this software system or assume any liability for its *
15// * use. Please see the license in the file LICENSE and URL above *
16// * for the full disclaimer and the limitation of liability. *
17// * *
18// * This code implementation is the result of the scientific and *
19// * technical work of the GEANT4 collaboration. *
20// * By using, copying, modifying or distributing the software (or *
21// * any work based on the software) you agree to acknowledge its *
22// * use in resulting scientific publications, and indicate your *
23// * acceptance of all terms of the Geant4 Software license. *
24// ********************************************************************
25//
26//
27// $Id$
28//
29//
30// G4 Physics class: G4QKaonPlusElasticCrossSection for pA elastic cross sections
31// Created: M.V. Kossov, CERN/ITEP(Moscow), 5-Feb-2010
32// The last update: M.V. Kossov, CERN/ITEP (Moscow) 5-Feb-2010
33//
34// -------------------------------------------------------------------------------
35// Short description: Interaction cross-sections for the G4QElastic process
36// -------------------------------------------------------------------------------
37
38//#define debug
39//#define isodebug
40//#define pdebug
41//#define ppdebug
42//#define tdebug
43//#define sdebug
44
46#include "G4SystemOfUnits.hh"
47
48// Initialization of the static parameters
49const G4int G4QKaonPlusElasticCrossSection::nPoints=128;//#ofPt in AMDB table(>anyPar)/D
50const G4int G4QKaonPlusElasticCrossSection::nLast=nPoints-1;// theLastElement inTable /D
51G4double G4QKaonPlusElasticCrossSection::lPMin=-8.; //Min tabulatedLogarithmMomentum/D
52G4double G4QKaonPlusElasticCrossSection::lPMax= 8.; //Max tabulatedLogarithmMomentum/D
53G4double G4QKaonPlusElasticCrossSection::dlnP=(lPMax-lPMin)/nLast;// LogStep inTable /D
54G4bool G4QKaonPlusElasticCrossSection::onlyCS=true;//Flag toCalculOnlyCS(not Si/Bi)/L
55G4double G4QKaonPlusElasticCrossSection::lastSIG=0.; //Last calculated cross section /L
56G4double G4QKaonPlusElasticCrossSection::lastLP=-10.;//LastLog(mom_of IncidentHadron)/L
57G4double G4QKaonPlusElasticCrossSection::lastTM=0.; //Last t_maximum /L
58G4double G4QKaonPlusElasticCrossSection::theSS=0.; //TheLastSqSlope of 1st difr.Max/L
59G4double G4QKaonPlusElasticCrossSection::theS1=0.; //TheLastMantissa of 1st difrMax/L
60G4double G4QKaonPlusElasticCrossSection::theB1=0.; //TheLastSlope of 1st difructMax/L
61G4double G4QKaonPlusElasticCrossSection::theS2=0.; //TheLastMantissa of 2nd difrMax/L
62G4double G4QKaonPlusElasticCrossSection::theB2=0.; //TheLastSlope of 2nd difructMax/L
63G4double G4QKaonPlusElasticCrossSection::theS3=0.; //TheLastMantissa of 3d difr.Max/L
64G4double G4QKaonPlusElasticCrossSection::theB3=0.; //TheLastSlope of 3d difruct.Max/L
65G4double G4QKaonPlusElasticCrossSection::theS4=0.; //TheLastMantissa of 4th difrMax/L
66G4double G4QKaonPlusElasticCrossSection::theB4=0.; //TheLastSlope of 4th difructMax/L
67G4int G4QKaonPlusElasticCrossSection::lastTZ=0; // Last atomic number of theTarget
68G4int G4QKaonPlusElasticCrossSection::lastTN=0; // Last # of neutrons in theTarget
69G4double G4QKaonPlusElasticCrossSection::lastPIN=0.;// Last initialized max momentum
70G4double* G4QKaonPlusElasticCrossSection::lastCST=0; // Elastic cross-section table
71G4double* G4QKaonPlusElasticCrossSection::lastPAR=0; // ParametersForFunctionCalculation
72G4double* G4QKaonPlusElasticCrossSection::lastSST=0; // E-dep ofSqardSlope of 1st difMax
73G4double* G4QKaonPlusElasticCrossSection::lastS1T=0; // E-dep of mantissa of 1st dif.Max
74G4double* G4QKaonPlusElasticCrossSection::lastB1T=0; // E-dep of the slope of 1st difMax
75G4double* G4QKaonPlusElasticCrossSection::lastS2T=0; // E-dep of mantissa of 2nd difrMax
76G4double* G4QKaonPlusElasticCrossSection::lastB2T=0; // E-dep of the slope of 2nd difMax
77G4double* G4QKaonPlusElasticCrossSection::lastS3T=0; // E-dep of mantissa of 3d difr.Max
78G4double* G4QKaonPlusElasticCrossSection::lastB3T=0; // E-dep of the slope of 3d difrMax
79G4double* G4QKaonPlusElasticCrossSection::lastS4T=0; // E-dep of mantissa of 4th difrMax
80G4double* G4QKaonPlusElasticCrossSection::lastB4T=0; // E-dep of the slope of 4th difMax
81G4int G4QKaonPlusElasticCrossSection::lastN=0; // The last N of calculated nucleus
82G4int G4QKaonPlusElasticCrossSection::lastZ=0; // The last Z of calculated nucleus
83G4double G4QKaonPlusElasticCrossSection::lastP=0.; // LastUsed inCrossSection Momentum
84G4double G4QKaonPlusElasticCrossSection::lastTH=0.; // Last threshold momentum
85G4double G4QKaonPlusElasticCrossSection::lastCS=0.; // Last value of the Cross Section
86G4int G4QKaonPlusElasticCrossSection::lastI=0; // The last position in the DAMDB
87
88std::vector<G4double*> G4QKaonPlusElasticCrossSection::PAR;//Vector ofParsForFunctCalcul
89std::vector<G4double*> G4QKaonPlusElasticCrossSection::CST;//Vector ofCrossSection table
90std::vector<G4double*> G4QKaonPlusElasticCrossSection::SST;//Vector ofThe1st SquardSlope
91std::vector<G4double*> G4QKaonPlusElasticCrossSection::S1T;//Vector of the 1st mantissa
92std::vector<G4double*> G4QKaonPlusElasticCrossSection::B1T;//Vector of the1st slope
93std::vector<G4double*> G4QKaonPlusElasticCrossSection::S2T;//Vector of the2nd mantissa
94std::vector<G4double*> G4QKaonPlusElasticCrossSection::B2T;//Vector of the2nd slope
95std::vector<G4double*> G4QKaonPlusElasticCrossSection::S3T;//Vector of the3d mantissa
96std::vector<G4double*> G4QKaonPlusElasticCrossSection::B3T;//Vector of the3d slope
97std::vector<G4double*> G4QKaonPlusElasticCrossSection::S4T;//Vector ofThe4th mantissa(g)
98std::vector<G4double*> G4QKaonPlusElasticCrossSection::B4T;//Vector ofThe4th slope(glor)
99
101{
102}
103
105{
106 std::vector<G4double*>::iterator pos;
107 for (pos=CST.begin(); pos<CST.end(); pos++)
108 { delete [] *pos; }
109 CST.clear();
110 for (pos=PAR.begin(); pos<PAR.end(); pos++)
111 { delete [] *pos; }
112 PAR.clear();
113 for (pos=SST.begin(); pos<SST.end(); pos++)
114 { delete [] *pos; }
115 SST.clear();
116 for (pos=S1T.begin(); pos<S1T.end(); pos++)
117 { delete [] *pos; }
118 S1T.clear();
119 for (pos=B1T.begin(); pos<B1T.end(); pos++)
120 { delete [] *pos; }
121 B1T.clear();
122 for (pos=S2T.begin(); pos<S2T.end(); pos++)
123 { delete [] *pos; }
124 S2T.clear();
125 for (pos=B2T.begin(); pos<B2T.end(); pos++)
126 { delete [] *pos; }
127 B2T.clear();
128 for (pos=S3T.begin(); pos<S3T.end(); pos++)
129 { delete [] *pos; }
130 S3T.clear();
131 for (pos=B3T.begin(); pos<B3T.end(); pos++)
132 { delete [] *pos; }
133 B3T.clear();
134 for (pos=S4T.begin(); pos<S4T.end(); pos++)
135 { delete [] *pos; }
136 S4T.clear();
137 for (pos=B4T.begin(); pos<B4T.end(); pos++)
138 { delete [] *pos; }
139 B4T.clear();
140}
141
142// Returns Pointer to the G4VQCrossSection class
144{
145 static G4QKaonPlusElasticCrossSection theCrossSection;//StaticBody of the QElCrossSect
146 return &theCrossSection;
147}
148
149// The main member function giving the collision cross section (P is in IU, CS is in mb)
150// Make pMom in independent units ! (Now it is MeV)
152 G4int tgZ, G4int tgN, G4int pPDG)
153{
154 static std::vector <G4int> colN; // Vector of N for calculated nuclei (isotops)
155 static std::vector <G4int> colZ; // Vector of Z for calculated nuclei (isotops)
156 static std::vector <G4double> colP; // Vector of last momenta for the reaction
157 static std::vector <G4double> colTH; // Vector of energy thresholds for the reaction
158 static std::vector <G4double> colCS; // Vector of last cross sections for the reaction
159 // ***---*** End of the mandatory Static Definitions of the Associative Memory ***---***
160 G4double pEn=pMom;
161 onlyCS=fCS;
162#ifdef pdebug
163 G4cout<<"G4QKaPlusElCS::GetCS:>>>f="<<fCS<<", p="<<pMom<<", Z="<<tgZ<<"("<<lastZ<<") ,N="
164 <<tgN<<"("<<lastN<<"), T="<<pEn<<"("<<lastTH<<")"<<",Sz="<<colN.size()<<G4endl;
165 //CalculateCrossSection(fCS,-27,j,pPDG,lastZ,lastN,pMom); // DUMMY TEST
166#endif
167 if(pPDG!=321)
168 {
169 G4cout<<"*Warning*G4QKaonPlusElaCS::GetCS:*>Found pPDG="<<pPDG<<" ==> CS=0"<<G4endl;
170 //CalculateCrossSection(fCS,-27,j,pPDG,lastZ,lastN,pMom); // DUMMY TEST
171 return 0.; // projectile PDG=0 is a mistake (?!) @@
172 }
173 G4bool in=false; // By default the isotope must be found in the AMDB
174 lastP = 0.; // New momentum history (nothing to compare with)
175 lastN = tgN; // The last N of the calculated nucleus
176 lastZ = tgZ; // The last Z of the calculated nucleus
177 lastI = colN.size(); // Size of the Associative Memory DB in the heap
178 if(lastI) for(G4int i=0; i<lastI; i++) // Loop over proj/tgZ/tgN lines of DB
179 { // The nucleus with projPDG is found in AMDB
180 if(colN[i]==tgN && colZ[i]==tgZ) // Isotope is foind in AMDB
181 {
182 lastI=i;
183 lastTH =colTH[i]; // Last THreshold (A-dependent)
184#ifdef pdebug
185 G4cout<<"G4QKPElCS::GetCS:*Found* P="<<pMom<<",Threshold="<<lastTH<<",i="<<i<<G4endl;
186 //CalculateCrossSection(fCS,-27,i,pPDG,lastZ,lastN,pMom); // DUMMY TEST
187#endif
188 if(pEn<=lastTH)
189 {
190#ifdef pdebug
191 G4cout<<"G4QKPElCS::GetCS:Found T="<<pEn<<" < Threshold="<<lastTH<<",CS=0"<<G4endl;
192 //CalculateCrossSection(fCS,-27,i,pPDG,lastZ,lastN,pMom); // DUMMY TEST
193#endif
194 return 0.; // Energy is below the Threshold value
195 }
196 lastP =colP [i]; // Last Momentum (A-dependent)
197 lastCS =colCS[i]; // Last CrossSect (A-dependent)
198 // if(std::fabs(lastP/pMom-1.)<tolerance) //VI (do not use tolerance)
199 if(lastP == pMom) // Do not recalculate
200 {
201#ifdef pdebug
202 G4cout<<"G4QKaonPlusElastCS::GetCS: P="<<pMom<<",CS="<<lastCS*millibarn<<G4endl;
203#endif
204 CalculateCrossSection(fCS,-1,i,pPDG,lastZ,lastN,pMom); // Update param's only
205 return lastCS*millibarn; // Use theLastCS
206 }
207 in = true; // This is the case when the isotop is found in DB
208 // Momentum pMom is in IU ! @@ Units
209#ifdef pdebug
210 G4cout<<"G4QKPElCS::G:UpdateDB P="<<pMom<<",f="<<fCS<<",I="<<lastI<<",i="<<i<<G4endl;
211#endif
212 lastCS=CalculateCrossSection(fCS,-1,i,pPDG,lastZ,lastN,pMom); // read & update
213#ifdef pdebug
214 G4cout<<"G4QKaonPlusElCS::GetCrosSec:****>New(inDB) Calculated CS="<<lastCS<<G4endl;
215 //CalculateCrossSection(fCS,-27,i,pPDG,lastZ,lastN,pMom); // DUMMY TEST
216#endif
217 if(lastCS<=0. && pEn>lastTH) // Correct the threshold
218 {
219#ifdef pdebug
220 G4cout<<"G4QKaonPlusElCS::GetCS: T="<<pEn<<"(CS=0) > Threshold="<<lastTH<<G4endl;
221#endif
222 lastTH=pEn;
223 }
224 break; // Go out of the LOOP with found lastI
225 }
226#ifdef pdebug
227 G4cout<<"---G4QKaonPlusElasticCrossSection::GetCrosSec:pPDG="<<pPDG<<",i="<<i<<",N="
228 <<colN[i]<<",Z["<<i<<"]="<<colZ[i]<<G4endl;
229 //CalculateCrossSection(fCS,-27,i,pPDG,lastZ,lastN,pMom); // DUMMY TEST
230#endif
231 } // End of attampt to find the nucleus in DB
232 if(!in) // This nucleus has not been calculated previously
233 {
234#ifdef pdebug
235 G4cout<<"G4QKaonPlusElCS::GetCS:CalNewP="<<pMom<<",f="<<fCS<<",lastI="<<lastI<<G4endl;
236#endif
237 //!!The slave functions must provide cross-sections in millibarns (mb) !! (not in IU)
238 lastCS=CalculateCrossSection(fCS,0,lastI,pPDG,lastZ,lastN,pMom);//calculate&create
239 if(lastCS<=0.)
240 {
241 lastTH = ThresholdEnergy(tgZ, tgN); // The Threshold Energy which is now the last
242#ifdef pdebug
243 G4cout<<"G4QKaonPlusElasticCrossSection::GetCS:NewThr="<<lastTH<<",T="<<pEn<<G4endl;
244#endif
245 if(pEn>lastTH)
246 {
247#ifdef pdebug
248 G4cout<<"G4QKaonPlusElCS::GetCS:1st T="<<pEn<<"(CS=0)>Threshold="<<lastTH<<G4endl;
249#endif
250 lastTH=pEn;
251 }
252 }
253#ifdef pdebug
254 G4cout<<"G4QKaonPlusElCS::GetCS:NCS="<<lastCS<<",lZ="<<lastN<<",lN="<<lastZ<<G4endl;
255 //CalculateCrossSection(fCS,-27,lastI,pPDG,lastZ,lastN,pMom); // DUMMY TEST
256#endif
257 colN.push_back(tgN);
258 colZ.push_back(tgZ);
259 colP.push_back(pMom);
260 colTH.push_back(lastTH);
261 colCS.push_back(lastCS);
262#ifdef pdebug
263 G4cout<<"G4QKPElCS::GetCS:1st,P="<<pMom<<"(MeV),CS="<<lastCS*millibarn<<"(mb)"<<G4endl;
264 //CalculateCrossSection(fCS,-27,lastI,pPDG,lastZ,lastN,pMom); // DUMMY TEST
265#endif
266 return lastCS*millibarn;
267 } // End of creation of the new set of parameters
268 else
269 {
270#ifdef pdebug
271 G4cout<<"G4QKaonPlusElasticCrossSection::GetCS: Update lastI="<<lastI<<G4endl;
272#endif
273 colP[lastI]=pMom;
274 colCS[lastI]=lastCS;
275 }
276#ifdef pdebug
277 G4cout<<"G4QKPElCS::GetCSec:End,P="<<pMom<<"(MeV),CS="<<lastCS*millibarn<<"(mb)"<<G4endl;
278 //CalculateCrossSection(fCS,-27,lastI,pPDG,lastZ,lastN,pMom); // DUMMY TEST
279 G4cout<<"G4QKaonPlusElasticCrossSection::GetCrosSec:**End**, onlyCS="<<onlyCS<<G4endl;
280#endif
281 return lastCS*millibarn;
282}
283
284// Calculation of total elastic cross section (p in IU, CS in mb) @@ Units (?)
285// F=0 - create AMDB, F=-1 - read&update AMDB, F=1 - update AMDB (sinchro with higher AMDB)
287 G4int I, G4int PDG, G4int tgZ, G4int tgN, G4double pIU)
288{
289 // *** Begin of Associative Memory DB for acceleration of the cross section calculations
290 static std::vector <G4double> PIN; // Vector of max initialized log(P) in the table
291 // *** End of Static Definitions (Associative Memory Data Base) ***
292 G4double pMom=pIU/GeV; // All calculations are in GeV
293 onlyCS=CS; // Flag to calculate only CS (not Si/Bi)
294#ifdef pdebug
295 G4cout<<"G4QKaonPlusElasticCS::CalcCS: onlyCS="<<onlyCS<<",F="<<F<<",p="<<pIU<<G4endl;
296#endif
297 lastLP=std::log(pMom); // Make a logarithm of the momentum for calculation
298 if(F) // This isotope was found in AMDB =>RETRIEVE/UPDATE
299 {
300 if(F<0) // the AMDB must be loded
301 {
302 lastPIN = PIN[I]; // Max log(P) initialised for this table set
303 lastPAR = PAR[I]; // Pointer to the parameter set
304 lastCST = CST[I]; // Pointer to the total sross-section table
305 lastSST = SST[I]; // Pointer to the first squared slope
306 lastS1T = S1T[I]; // Pointer to the first mantissa
307 lastB1T = B1T[I]; // Pointer to the first slope
308 lastS2T = S2T[I]; // Pointer to the second mantissa
309 lastB2T = B2T[I]; // Pointer to the second slope
310 lastS3T = S3T[I]; // Pointer to the third mantissa
311 lastB3T = B3T[I]; // Pointer to the rhird slope
312 lastS4T = S4T[I]; // Pointer to the 4-th mantissa
313 lastB4T = B4T[I]; // Pointer to the 4-th slope
314#ifdef pdebug
315 G4cout<<"G4QKaonPlusElCS::CalCS:DB updated for I="<<I<<",*,PIN4="<<PIN[4]<<G4endl;
316#endif
317 }
318#ifdef pdebug
319 G4cout<<"G4QKaonPlusElasticCS::CalcCS:*read*,LP="<<lastLP<<",PIN="<<lastPIN<<G4endl;
320#endif
321 if(lastLP>lastPIN && lastLP<lPMax)
322 {
323 lastPIN=GetPTables(lastLP,lastPIN,PDG,tgZ,tgN);// Can update upper logP-Limit in tabs
324#ifdef pdebug
325 G4cout<<"G4QKPElCS::CalcCS:updated(I),LP="<<lastLP<<"<IN["<<I<<"]="<<lastPIN<<G4endl;
326#endif
327 PIN[I]=lastPIN; // Remember the new P-Limit of the tables
328 }
329 }
330 else // This isotope wasn't initialized => CREATE
331 {
332 lastPAR = new G4double[nPoints]; // Allocate memory for parameters of CS function
333 lastPAR[nLast]=0; // Initialization for VALGRIND
334 lastCST = new G4double[nPoints]; // Allocate memory for Tabulated CS function
335 lastSST = new G4double[nPoints]; // Allocate memory for Tabulated first sqaredSlope
336 lastS1T = new G4double[nPoints]; // Allocate memory for Tabulated first mantissa
337 lastB1T = new G4double[nPoints]; // Allocate memory for Tabulated first slope
338 lastS2T = new G4double[nPoints]; // Allocate memory for Tabulated second mantissa
339 lastB2T = new G4double[nPoints]; // Allocate memory for Tabulated second slope
340 lastS3T = new G4double[nPoints]; // Allocate memory for Tabulated third mantissa
341 lastB3T = new G4double[nPoints]; // Allocate memory for Tabulated third slope
342 lastS4T = new G4double[nPoints]; // Allocate memory for Tabulated 4-th mantissa
343 lastB4T = new G4double[nPoints]; // Allocate memory for Tabulated 4-th slope
344#ifdef pdebug
345 G4cout<<"G4QKaonPlusElasticCS::CalcCS:*ini*,lstLP="<<lastLP<<",min="<<lPMin<<G4endl;
346#endif
347 lastPIN = GetPTables(lastLP,lPMin,PDG,tgZ,tgN); // Returns the new P-limit for tables
348#ifdef pdebug
349 G4cout<<"G4QKaPlElCS::CCS:i,Z="<<tgZ<<",N="<<tgN<<",PDG="<<PDG<<",LP"<<lastPIN<<G4endl;
350#endif
351 PIN.push_back(lastPIN); // Fill parameters of CS function to AMDB
352 PAR.push_back(lastPAR); // Fill parameters of CS function to AMDB
353 CST.push_back(lastCST); // Fill Tabulated CS function to AMDB
354 SST.push_back(lastSST); // Fill Tabulated first sq.slope to AMDB
355 S1T.push_back(lastS1T); // Fill Tabulated first mantissa to AMDB
356 B1T.push_back(lastB1T); // Fill Tabulated first slope to AMDB
357 S2T.push_back(lastS2T); // Fill Tabulated second mantissa to AMDB
358 B2T.push_back(lastB2T); // Fill Tabulated second slope to AMDB
359 S3T.push_back(lastS3T); // Fill Tabulated third mantissa to AMDB
360 B3T.push_back(lastB3T); // Fill Tabulated third slope to AMDB
361 S4T.push_back(lastS4T); // Fill Tabulated 4-th mantissa to AMDB
362 B4T.push_back(lastB4T); // Fill Tabulated 4-th slope to AMDB
363 } // End of creation/update of the new set of parameters and tables
364 // =----------= NOW Update (if necessary) and Calculate the Cross Section =----------=
365#ifdef pdebug
366 G4cout<<"G4QKPElCS::CalcCS:?update?,LP="<<lastLP<<",IN="<<lastPIN<<",ML="<<lPMax<<G4endl;
367#endif
368 if(lastLP>lastPIN && lastLP<lPMax)
369 {
370 lastPIN = GetPTables(lastLP,lastPIN,PDG,tgZ,tgN);
371#ifdef pdebug
372 G4cout<<"G4QKaonPlusElCS::CalcCS:*updated(O)*,LP="<<lastLP<<"<IN="<<lastPIN<<G4endl;
373#endif
374 }
375#ifdef pdebug
376 G4cout<<"G4QKaPlElCS::CalcCS:lastLP="<<lastLP<<",lPM="<<lPMin<<",lPIN="<<lastPIN<<G4endl;
377#endif
378 if(!onlyCS) lastTM=GetQ2max(PDG, tgZ, tgN, pMom); // Calculate (-t)_max=Q2_max (GeV2)
379#ifdef pdebug
380 G4cout<<"G4QKaPlElCrosSec::CalcCS: oCS="<<onlyCS<<",-t="<<lastTM<<", p="<<lastLP<<G4endl;
381#endif
382 if(lastLP>lPMin && lastLP<=lastPIN) // Linear fit is made using precalculated tables
383 {
384 if(lastLP==lastPIN)
385 {
386 G4double shift=(lastLP-lPMin)/dlnP+.000001; // Log distance from lPMin
387 G4int blast=static_cast<int>(shift); // this is a bin number of the lower edge (0)
388 if(blast<0 || blast>=nLast) G4cout<<"G4QKPElCS::CCS:b="<<blast<<",n="<<nLast<<G4endl;
389 lastSIG = lastCST[blast];
390 if(!onlyCS) // Skip the differential cross-section parameters
391 {
392 theSS = lastSST[blast];
393 theS1 = lastS1T[blast];
394 theB1 = lastB1T[blast];
395 theS2 = lastS2T[blast];
396 theB2 = lastB2T[blast];
397 theS3 = lastS3T[blast];
398 theB3 = lastB3T[blast];
399 theS4 = lastS4T[blast];
400 theB4 = lastB4T[blast];
401 }
402#ifdef pdebug
403 G4cout<<"G4QKaonPlusElasticCS::CalculateCS:(E) S1="<<theS1<<",B1="<<theB1<<G4endl;
404#endif
405 }
406 else
407 {
408 G4double shift=(lastLP-lPMin)/dlnP; // a shift from the beginning of the table
409 G4int blast=static_cast<int>(shift); // the lower bin number
410 if(blast<0) blast=0;
411 if(blast>=nLast) blast=nLast-1; // low edge of the last bin
412 shift-=blast; // step inside the unit bin
413 G4int lastL=blast+1; // the upper bin number
414 G4double SIGL=lastCST[blast]; // the basic value of the cross-section
415 lastSIG= SIGL+shift*(lastCST[lastL]-SIGL); // calculated total elastic cross-section
416#ifdef pdebug
417 G4cout<<"G4QKaonPlusElasticCrossSection::CalcCrossSection:Sig="<<lastSIG<<",P="
418 <<pMom<<",Z="<<tgZ<<",N="<<tgN<<",PDG="<<PDG<<",onlyCS="<<onlyCS<<G4endl;
419#endif
420 if(!onlyCS) // Skip the differential cross-section parameters
421 {
422 G4double SSTL=lastSST[blast]; // the low bin of the first squared slope
423 theSS=SSTL+shift*(lastSST[lastL]-SSTL); // the basic value of the first sq.slope
424 G4double S1TL=lastS1T[blast]; // the low bin of the first mantissa
425 theS1=S1TL+shift*(lastS1T[lastL]-S1TL); // the basic value of the first mantissa
426 G4double B1TL=lastB1T[blast]; // the low bin of the first slope
427#ifdef pdebug
428 G4cout<<"G4QKaonPlusElasticCS::CalcCrossSect: b="<<blast<<", ls="<<lastL<<",SL="
429 <<S1TL<<",SU="<<lastS1T[lastL]<<",BL="<<B1TL<<",BU="<<lastB1T[lastL]<<G4endl;
430#endif
431 theB1=B1TL+shift*(lastB1T[lastL]-B1TL); // the basic value of the first slope
432 G4double S2TL=lastS2T[blast]; // the low bin of the second mantissa
433 theS2=S2TL+shift*(lastS2T[lastL]-S2TL); // the basic value of the second mantissa
434 G4double B2TL=lastB2T[blast]; // the low bin of the second slope
435 theB2=B2TL+shift*(lastB2T[lastL]-B2TL); // the basic value of the second slope
436 G4double S3TL=lastS3T[blast]; // the low bin of the third mantissa
437 theS3=S3TL+shift*(lastS3T[lastL]-S3TL); // the basic value of the third mantissa
438#ifdef pdebug
439 G4cout<<"G4QKaonPlusElasticCrossSection::CalcCS: s3l="<<S3TL<<", sh3="<<shift
440 <<", s3h="<<lastS3T[lastL]<<", b="<<blast<<", l="<<lastL<<G4endl;
441#endif
442 G4double B3TL=lastB3T[blast]; // the low bin of the third slope
443 theB3=B3TL+shift*(lastB3T[lastL]-B3TL); // the basic value of the third slope
444 G4double S4TL=lastS4T[blast]; // the low bin of the 4-th mantissa
445 theS4=S4TL+shift*(lastS4T[lastL]-S4TL); // the basic value of the 4-th mantissa
446#ifdef pdebug
447 G4cout<<"G4QKaonPlusElasticCrossSection::CalcCS: s4l="<<S4TL<<", sh4="<<shift
448 <<",s4h="<<lastS4T[lastL]<<",b="<<blast<<",l="<<lastL<<G4endl;
449#endif
450 G4double B4TL=lastB4T[blast]; // the low bin of the 4-th slope
451 theB4=B4TL+shift*(lastB4T[lastL]-B4TL); // the basic value of the 4-th slope
452 }
453#ifdef pdebug
454 G4cout<<"G4QKaonPlusElasticCS::CalculateCS:(I) S1="<<theS1<<",B1="<<theB1<<G4endl;
455#endif
456 }
457 }
458 else lastSIG=GetTabValues(lastLP, PDG, tgZ, tgN); // Direct calculation beyond the table
459 if(lastSIG<0.) lastSIG = 0.; // @@ a Warning print can be added
460#ifdef pdebug
461 G4cout<<"G4QKaonPlusElasticCrossSection::CalculateCS: END, onlyCS="<<onlyCS<<G4endl;
462#endif
463 return lastSIG;
464}
465
466// It has parameter sets for all tZ/tN/PDG, using them the tables can be created/updated
467G4double G4QKaonPlusElasticCrossSection::GetPTables(G4double LP,G4double ILP, G4int PDG,
468 G4int tgZ, G4int tgN)
469{
470 // @@ At present all nA==pA ---------> Each neucleus can have not more than 51 parameters
471 static const G4double pwd=2727;
472 const G4int n_kppel=35; // #of parameters for pp-elastic (<nPoints=128)
473 // -0--1- -2- -3- -4- -5- -6--7--8--9- -10--11-12--13--14-
474 G4double kpp_el[n_kppel]={.7,.38,.0676,.0557,3.5,2.23,.7,.1,2.,1.,.372,5.,74.,3.,3.4,
475 .2,.17,.001,8.,.055,3.64,5.e-5,4000.,1500.,.46,1.2e6,3.5e6,
476 5.e-5,1.e10,8.5e8,1.e10,1.1,3.4e6,6.8e6,0.};
477 // -15--16--17--18--19- -20- -21- -22- -23- -24- -25- -26-
478 // -27- -28- -29- -30- -31- -32- -33--34-
479
480 if(PDG == 321)
481 {
482 // -- Total pp elastic cross section cs & s1/b1 (main), s2/b2 (tail1), s3/b3 (tail2) --
483 //p2=p*p;p3=p2*p;sp=sqrt(p);p2s=p2*sp;lp=log(p);dl1=lp-(3.=par(3));p4=p2*p2; p=|3-mom|
484 //CS=2.865/p2s/(1+.0022/p2s)+(18.9+.6461*dl1*dl1+9./p)/(1.+.425*lp)/(1.+.4276/p4);
485 // par(0) par(7) par(1) par(2) par(4) par(5) par(6)
486 //dl2=lp-5., s1=(74.+3.*dl2*dl2)/(1+3.4/p4/p)+(.2/p2+17.*p)/(p4+.001*sp),
487 // par(8) par(9) par(10) par(11) par(12)par(13) par(14)
488 // b1=8.*p**.055/(1.+3.64/p3); s2=5.e-5+4000./(p4+1500.*p); b2=.46+1.2e6/(p4+3.5e6/sp);
489 // par(15) par(16) par(17) par(18) par(19) par(20) par(21) par(22) par(23)
490 // s3=5.e-5+1.e10/(p4*p4+8.5e8*p2+1.e10); b3=1.1+3.4e6/(p4+6.8e6); ss=0.
491 // par(24) par(25) par(26) par(27) par(28) par(29) par(30) par(31)
492 //
493 if(lastPAR[nLast]!=pwd) // A unique flag to avoid the repeatable definition
494 {
495 if ( tgZ == 1 && tgN == 0 )
496 {
497 for (G4int ip=0; ip<n_kppel; ip++) lastPAR[ip]=kpp_el[ip]; // KPlus+P
498 }
499 else
500 {
501 G4double a=tgZ+tgN;
502 G4double sa=std::sqrt(a);
503 G4double ssa=std::sqrt(sa);
504 G4double asa=a*sa;
505 G4double a2=a*a;
506 G4double a3=a2*a;
507 G4double a4=a3*a;
508 G4double a5=a4*a;
509 G4double a6=a4*a2;
510 G4double a7=a6*a;
511 G4double a8=a7*a;
512 G4double a9=a8*a;
513 G4double a10=a5*a5;
514 G4double a12=a6*a6;
515 G4double a14=a7*a7;
516 G4double a16=a8*a8;
517 G4double a17=a16*a;
518 //G4double a20=a16*a4;
519 G4double a32=a16*a16;
520 // Reaction cross-section parameters (kpael_fit.f)
521 lastPAR[0]=.06*asa/(1.+a*(.01+.1/ssa)); // p1
522 lastPAR[1]=.75*asa/(1.+.009*a); // p2
523 lastPAR[2]=.9*asa*ssa/(1.+.03*a); // p3
524 lastPAR[3]=3.; // p4
525 lastPAR[4]=4.2; // p5
526 lastPAR[5]=0.; // p6 not used
527 lastPAR[6]=0.; // p7 not used
528 lastPAR[7]=0.; // p8 not used
529 lastPAR[8]=0.; // p9 not used
530 // @@ the differential cross-section is parameterized separately for A>6 & A<7
531 if(a<6.5)
532 {
533 G4double a28=a16*a12;
534 // The main pre-exponent (pel_sg)
535 lastPAR[ 9]=4000*a; // p1
536 lastPAR[10]=1.2e7*a8+380*a17; // p2
537 lastPAR[11]=.7/(1.+4.e-12*a16); // p3
538 lastPAR[12]=2.5/a8/(a4+1.e-16*a32); // p4
539 lastPAR[13]=.28*a; // p5
540 lastPAR[14]=1.2*a2+2.3; // p6
541 lastPAR[15]=3.8/a; // p7
542 // The main slope (pel_sl)
543 lastPAR[16]=.01/(1.+.0024*a5); // p1
544 lastPAR[17]=.2*a; // p2
545 lastPAR[18]=9.e-7/(1.+.035*a5); // p3
546 lastPAR[19]=(42.+2.7e-11*a16)/(1.+.14*a); // p4
547 // The main quadratic (pel_sh)
548 lastPAR[20]=2.25*a3; // p1
549 lastPAR[21]=18.; // p2
550 lastPAR[22]=2.4e-3*a8/(1.+2.6e-4*a7); // p3
551 lastPAR[23]=3.5e-36*a32*a8/(1.+5.e-15*a32/a); // p4
552 // The 1st max pre-exponent (pel_qq)
553 lastPAR[24]=1.e5/(a8+2.5e12/a16); // p1
554 lastPAR[25]=8.e7/(a12+1.e-27*a28*a28); // p2
555 lastPAR[26]=.0006*a3; // p3
556 // The 1st max slope (pel_qs)
557 lastPAR[27]=10.+4.e-8*a12*a; // p1
558 lastPAR[28]=.114; // p2
559 lastPAR[29]=.003; // p3
560 lastPAR[30]=2.e-23; // p4
561 // The effective pre-exponent (pel_ss)
562 lastPAR[31]=1./(1.+.0001*a8); // p1
563 lastPAR[32]=1.5e-4/(1.+5.e-6*a12); // p2
564 lastPAR[33]=.03; // p3
565 // The effective slope (pel_sb)
566 lastPAR[34]=a/2; // p1
567 lastPAR[35]=2.e-7*a4; // p2
568 lastPAR[36]=4.; // p3
569 lastPAR[37]=64./a3; // p4
570 // The gloria pre-exponent (pel_us)
571 lastPAR[38]=1.e8*std::exp(.32*asa); // p1
572 lastPAR[39]=20.*std::exp(.45*asa); // p2
573 lastPAR[40]=7.e3+2.4e6/a5; // p3
574 lastPAR[41]=2.5e5*std::exp(.085*a3); // p4
575 lastPAR[42]=2.5*a; // p5
576 // The gloria slope (pel_ub)
577 lastPAR[43]=920.+.03*a8*a3; // p1
578 lastPAR[44]=93.+.0023*a12; // p2
579#ifdef pdebug
580 G4cout<<"G4QKPElCS::CalcCS:la "<<lastPAR[38]<<", "<<lastPAR[39]<<", "<<lastPAR[40]
581 <<", "<<lastPAR[42]<<", "<<lastPAR[43]<<", "<<lastPAR[44]<<G4endl;
582#endif
583 }
584 else
585 {
586 G4double p1a10=2.2e-28*a10;
587 G4double r4a16=6.e14/a16;
588 G4double s4a16=r4a16*r4a16;
589 // a24
590 // a36
591 // The main pre-exponent (peh_sg)
592 lastPAR[ 9]=4.5*std::pow(a,1.15); // p1
593 lastPAR[10]=.06*std::pow(a,.6); // p2
594 lastPAR[11]=.6*a/(1.+2.e15/a16); // p3
595 lastPAR[12]=.17/(a+9.e5/a3+1.5e33/a32); // p4
596 lastPAR[13]=(.001+7.e-11*a5)/(1.+4.4e-11*a5); // p5
597 lastPAR[14]=(p1a10*p1a10+2.e-29)/(1.+2.e-22*a12); // p6
598 // The main slope (peh_sl)
599 lastPAR[15]=400./a12+2.e-22*a9; // p1
600 lastPAR[16]=1.e-32*a12/(1.+5.e22/a14); // p2
601 lastPAR[17]=1000./a2+9.5*sa*ssa; // p3
602 lastPAR[18]=4.e-6*a*asa+1.e11/a16; // p4
603 lastPAR[19]=(120./a+.002*a2)/(1.+2.e14/a16); // p5
604 lastPAR[20]=9.+100./a; // p6
605 // The main quadratic (peh_sh)
606 lastPAR[21]=.002*a3+3.e7/a6; // p1
607 lastPAR[22]=7.e-15*a4*asa; // p2
608 lastPAR[23]=9000./a4; // p3
609 // The 1st max pre-exponent (peh_qq)
610 lastPAR[24]=.0011*asa/(1.+3.e34/a32/a4); // p1
611 lastPAR[25]=1.e-5*a2+2.e14/a16; // p2
612 lastPAR[26]=1.2e-11*a2/(1.+1.5e19/a12); // p3
613 lastPAR[27]=.016*asa/(1.+5.e16/a16); // p4
614 // The 1st max slope (peh_qs)
615 lastPAR[28]=.002*a4/(1.+7.e7/std::pow(a-6.83,14)); // p1
616 lastPAR[29]=2.e6/a6+7.2/std::pow(a,.11); // p2
617 lastPAR[30]=11.*a3/(1.+7.e23/a16/a8); // p3
618 lastPAR[31]=100./asa; // p4
619 // The 2nd max pre-exponent (peh_ss)
620 lastPAR[32]=(.1+4.4e-5*a2)/(1.+5.e5/a4); // p1
621 lastPAR[33]=3.5e-4*a2/(1.+1.e8/a8); // p2
622 lastPAR[34]=1.3+3.e5/a4; // p3
623 lastPAR[35]=500./(a2+50.)+3; // p4
624 lastPAR[36]=1.e-9/a+s4a16*s4a16; // p5
625 // The 2nd max slope (peh_sb)
626 lastPAR[37]=.4*asa+3.e-9*a6; // p1
627 lastPAR[38]=.0005*a5; // p2
628 lastPAR[39]=.002*a5; // p3
629 lastPAR[40]=10.; // p4
630 // The effective pre-exponent (peh_us)
631 lastPAR[41]=.05+.005*a; // p1
632 lastPAR[42]=7.e-8/sa; // p2
633 lastPAR[43]=.8*sa; // p3
634 lastPAR[44]=.02*sa; // p4
635 lastPAR[45]=1.e8/a3; // p5
636 lastPAR[46]=3.e32/(a32+1.e32); // p6
637 // The effective slope (peh_ub)
638 lastPAR[47]=24.; // p1
639 lastPAR[48]=20./sa; // p2
640 lastPAR[49]=7.e3*a/(sa+1.); // p3
641 lastPAR[50]=900.*sa/(1.+500./a3); // p4
642#ifdef pdebug
643 G4cout<<"G4QKPElCS::CalcCS:ha "<<lastPAR[41]<<", "<<lastPAR[42]<<", "<<lastPAR[43]
644 <<", "<<lastPAR[44]<<", "<<lastPAR[45]<<", "<<lastPAR[46]<<G4endl;
645#endif
646 }
647 // Parameter for lowEnergyNeutrons
648 lastPAR[51]=1.e15+2.e27/a4/(1.+2.e-18*a16);
649 }
650 lastPAR[nLast]=pwd;
651 // and initialize the zero element of the table
652 G4double lp=lPMin; // ln(momentum)
653 G4bool memCS=onlyCS; // ??
654 onlyCS=false;
655 lastCST[0]=GetTabValues(lp, PDG, tgZ, tgN); // Calculate AMDB tables
656 onlyCS=memCS;
657 lastSST[0]=theSS;
658 lastS1T[0]=theS1;
659 lastB1T[0]=theB1;
660 lastS2T[0]=theS2;
661 lastB2T[0]=theB2;
662 lastS3T[0]=theS3;
663 lastB3T[0]=theB3;
664 lastS4T[0]=theS4;
665 lastB4T[0]=theB4;
666#ifdef pdebug
667 G4cout<<"G4QKaonPlusElasticCrossSection::GetPTables:ip=0(init), lp="<<lp<<",S1="
668 <<theS1<<",B1="<<theB1<<",S2="<<theS2<<",B2="<<theB3<<",S3="<<theS3
669 <<",B3="<<theB3<<",S4="<<theS4<<",B4="<<theB4<<G4endl;
670#endif
671 }
672 if(LP>ILP)
673 {
674 G4int ini = static_cast<int>((ILP-lPMin+.000001)/dlnP)+1; // already inited till this
675 if(ini<0) ini=0;
676 if(ini<nPoints)
677 {
678 G4int fin = static_cast<int>((LP-lPMin)/dlnP)+1; // final bin of initialization
679 if(fin>=nPoints) fin=nLast; // Limit of the tabular initialization
680 if(fin>=ini)
681 {
682 G4double lp=0.;
683 for(G4int ip=ini; ip<=fin; ip++) // Calculate tabular CS,S1,B1,S2,B2,S3,B3
684 {
685 lp=lPMin+ip*dlnP; // ln(momentum)
686 G4bool memCS=onlyCS;
687 onlyCS=false;
688 lastCST[ip]=GetTabValues(lp, PDG, tgZ, tgN); // Calculate AMDB tables (ret CS)
689 onlyCS=memCS;
690 lastSST[ip]=theSS;
691 lastS1T[ip]=theS1;
692 lastB1T[ip]=theB1;
693 lastS2T[ip]=theS2;
694 lastB2T[ip]=theB2;
695 lastS3T[ip]=theS3;
696 lastB3T[ip]=theB3;
697 lastS4T[ip]=theS4;
698 lastB4T[ip]=theB4;
699#ifdef pdebug
700 G4cout<<"G4QKaonPlusElasticCrossSection::GetPTables:ip="<<ip<<",lp="<<lp
701 <<",S1="<<theS1<<",B1="<<theB1<<",S2="<<theS2<<",B2="<<theB2<<",S3="
702 <<theS3<<",B3="<<theB3<<",S4="<<theS4<<",B4="<<theB4<<G4endl;
703#endif
704 }
705 return lp;
706 }
707 else G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetPTables: PDG="<<PDG
708 <<", Z="<<tgZ<<", N="<<tgN<<", i="<<ini<<" > fin="<<fin<<", LP="<<LP
709 <<" > ILP="<<ILP<<" nothing is done!"<<G4endl;
710 }
711 else G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetPTables: PDG="<<PDG
712 <<", Z="<<tgZ<<", N="<<tgN<<", i="<<ini<<">= max="<<nPoints<<", LP="<<LP
713 <<" > ILP="<<ILP<<", lPMax="<<lPMax<<" nothing is done!"<<G4endl;
714 }
715#ifdef pdebug
716 else G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetPTa:PDG="<<PDG<<",Z="<<tgZ
717 <<", N="<<tgN<<", LP="<<LP<<" <= ILP="<<ILP<<" nothing is done!"<<G4endl;
718#endif
719 }
720 else
721 {
722 // G4cout<<"*Error*G4QKaonPlusElasticCrossSection::GetPTables: PDG="<<PDG<<", Z="<<tgZ
723 // <<", N="<<tgN<<", while it is defined only for PDG=321"<<G4endl;
724 // throw G4QException("G4QKaonPlusElasticCrossSection::GetPTables:onlyK+ is implemented");
726 ed << "PDG = " << PDG << ", Z = " << tgZ << ", N = " << tgN
727 << ", while it is defined only for PDG=321 (K+) " << G4endl;
728 G4Exception("G4QKaonPlusElasticCrossSection::GetPTables()", "HAD_CHPS_0000",
729 FatalException, ed);
730 }
731 return ILP;
732}
733
734// Returns Q2=-t in independent units (MeV^2) (all internal calculations are in GeV)
736{
737 static const G4double GeVSQ=gigaelectronvolt*gigaelectronvolt;
738 static const G4double third=1./3.;
739 static const G4double fifth=1./5.;
740 static const G4double sevth=1./7.;
741#ifdef tdebug
742 G4cout<<"G4QKaPlElCS::GetExchT:F="<<onlyCS<<",Z="<<tgZ<<",N="<<tgN<<",PDG="<<PDG<<G4endl;
743#endif
744 if(PDG!=321) G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetExT:PDG="<<PDG<<G4endl;
745 if(onlyCS) G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetExT: onlyCS=1"<<G4endl;
746 if(lastLP<-4.3) return lastTM*GeVSQ*G4UniformRand();// S-wave for p<14 MeV/c (kinE<.1MeV)
747 G4double q2=0.;
748 if(tgZ==1 && tgN==0) // ===> p+p=p+p
749 {
750#ifdef tdebug
751 G4cout<<"G4QKaonPlusElCS::GetExT: TM="<<lastTM<<",S1="<<theS1<<",B1="<<theB1<<",S2="
752 <<theS2<<",B2="<<theB2<<",S3="<<theS3<<",B3="<<theB3<<",GeV2="<<GeVSQ<<G4endl;
753#endif
754 G4double E1=lastTM*theB1;
755 G4double R1=(1.-std::exp(-E1));
756#ifdef tdebug
757 G4double ts1=-std::log(1.-R1)/theB1;
758 G4double ds1=std::fabs(ts1-lastTM)/lastTM;
759 if(ds1>.0001)
760 G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetExT:1p "<<ts1<<"#"<<lastTM
761 <<",d="<<ds1<<",R1="<<R1<<",E1="<<E1<<G4endl;
762#endif
763 G4double E2=lastTM*theB2;
764 G4double R2=(1.-std::exp(-E2*E2*E2));
765#ifdef tdebug
766 G4double ts2=std::pow(-std::log(1.-R2),.333333333)/theB2;
767 G4double ds2=std::fabs(ts2-lastTM)/lastTM;
768 if(ds2>.0001)
769 G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetExT:2p "<<ts2<<"#"<<lastTM
770 <<",d="<<ds2<<",R2="<<R2<<",E2="<<E2<<G4endl;
771#endif
772 G4double E3=lastTM*theB3;
773 G4double R3=(1.-std::exp(-E3));
774#ifdef tdebug
775 G4double ts3=-std::log(1.-R3)/theB3;
776 G4double ds3=std::fabs(ts3-lastTM)/lastTM;
777 if(ds3>.0001)
778 G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetExT:3p "<<ts3<<"#"<<lastTM
779 <<",d="<<ds3<<",R3="<<R1<<",E3="<<E3<<G4endl;
780#endif
781 G4double I1=R1*theS1/theB1;
782 G4double I2=R2*theS2;
783 G4double I3=R3*theS3;
784 G4double I12=I1+I2;
785 G4double rand=(I12+I3)*G4UniformRand();
786 if (rand<I1 )
787 {
788 G4double ran=R1*G4UniformRand();
789 if(ran>1.) ran=1.;
790 q2=-std::log(1.-ran)/theB1;
791 }
792 else if(rand<I12)
793 {
794 G4double ran=R2*G4UniformRand();
795 if(ran>1.) ran=1.;
796 q2=-std::log(1.-ran);
797 if(q2<0.) q2=0.;
798 q2=std::pow(q2,third)/theB2;
799 }
800 else
801 {
802 G4double ran=R3*G4UniformRand();
803 if(ran>1.) ran=1.;
804 q2=-std::log(1.-ran)/theB3;
805 }
806 }
807 else
808 {
809 G4double a=tgZ+tgN;
810#ifdef tdebug
811 G4cout<<"G4QKaonPlusElasticCrossSection::GetExT:a="<<a<<",t="<<lastTM<<",S1="<<theS1
812 <<",B1="<<theB1<<",SS="<<theSS<<",S2="<<theS2<<",B2="<<theB2<<",S3="<<theS3
813 <<",B3="<<theB3<<",S4="<<theS4<<",B4="<<theB4<<G4endl;
814#endif
815 G4double E1=lastTM*(theB1+lastTM*theSS);
816 G4double R1=(1.-std::exp(-E1));
817 G4double tss=theSS+theSS; // for future solution of quadratic equation (imediate check)
818#ifdef tdebug
819 G4double ts1=-std::log(1.-R1)/theB1;
820 if(std::fabs(tss)>1.e-7) ts1=(std::sqrt(theB1*(theB1+(tss+tss)*ts1))-theB1)/tss;
821 G4double ds1=(ts1-lastTM)/lastTM;
822 if(ds1>.0001)
823 G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetExT:1a "<<ts1<<"#"<<lastTM
824 <<",d="<<ds1<<",R1="<<R1<<",E1="<<E1<<G4endl;
825#endif
826 G4double tm2=lastTM*lastTM;
827 G4double E2=lastTM*tm2*theB2; // power 3 for lowA, 5 for HighA (1st)
828 if(a>6.5)E2*=tm2; // for heavy nuclei
829 G4double R2=(1.-std::exp(-E2));
830#ifdef tdebug
831 G4double ts2=-std::log(1.-R2)/theB2;
832 if(a<6.5)ts2=std::pow(ts2,third);
833 else ts2=std::pow(ts2,fifth);
834 G4double ds2=std::fabs(ts2-lastTM)/lastTM;
835 if(ds2>.0001)
836 G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetExT:2a "<<ts2<<"#"<<lastTM
837 <<",d="<<ds2<<",R2="<<R2<<",E2="<<E2<<G4endl;
838#endif
839 G4double E3=lastTM*theB3;
840 if(a>6.5)E3*=tm2*tm2*tm2; // power 1 for lowA, 7 (2nd) for HighA
841 G4double R3=(1.-std::exp(-E3));
842#ifdef tdebug
843 G4double ts3=-std::log(1.-R3)/theB3;
844 if(a>6.5)ts3=std::pow(ts3,sevth);
845 G4double ds3=std::fabs(ts3-lastTM)/lastTM;
846 if(ds3>.0001)
847 G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetExT:3a "<<ts3<<"#"<<lastTM
848 <<",d="<<ds3<<",R3="<<R3<<",E3="<<E3<<G4endl;
849#endif
850 G4double E4=lastTM*theB4;
851 G4double R4=(1.-std::exp(-E4));
852#ifdef tdebug
853 G4double ts4=-std::log(1.-R4)/theB4;
854 G4double ds4=std::fabs(ts4-lastTM)/lastTM;
855 if(ds4>.0001)
856 G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetExT:4a "<<ts4<<"#"<<lastTM
857 <<",d="<<ds4<<",R4="<<R4<<",E4="<<E4<<G4endl;
858#endif
859 G4double I1=R1*theS1;
860 G4double I2=R2*theS2;
861 G4double I3=R3*theS3;
862 G4double I4=R4*theS4;
863 G4double I12=I1+I2;
864 G4double I13=I12+I3;
865 G4double rand=(I13+I4)*G4UniformRand();
866#ifdef tdebug
867 G4cout<<"G4QKPElCS::GExT:1="<<I1<<",2="<<I2<<",3="<<I3<<",4="<<I4<<",r="<<rand<<G4endl;
868#endif
869 if(rand<I1)
870 {
871 G4double ran=R1*G4UniformRand();
872 if(ran>1.) ran=1.;
873 q2=-std::log(1.-ran)/theB1;
874 if(std::fabs(tss)>1.e-7) q2=(std::sqrt(theB1*(theB1+(tss+tss)*q2))-theB1)/tss;
875#ifdef tdebug
876 G4cout<<"G4QKPElCS::GExT:Q2="<<q2<<",ss="<<tss/2<<",b1="<<theB1<<",t1="<<ts1<<G4endl;
877#endif
878 }
879 else if(rand<I12)
880 {
881 G4double ran=R2*G4UniformRand();
882 if(ran>1.) ran=1.;
883 q2=-std::log(1.-ran)/theB2;
884 if(q2<0.) q2=0.;
885 if(a<6.5) q2=std::pow(q2,third);
886 else q2=std::pow(q2,fifth);
887#ifdef tdebug
888 G4cout<<"G4QKPElCS::GetExT: Q2="<<q2<<",r2="<<R2<<",b2="<<theB2<<",t2="<<ts2<<G4endl;
889#endif
890 }
891 else if(rand<I13)
892 {
893 G4double ran=R3*G4UniformRand();
894 if(ran>1.) ran=1.;
895 q2=-std::log(1.-ran)/theB3;
896 if(q2<0.) q2=0.;
897 if(a>6.5) q2=std::pow(q2,sevth);
898#ifdef tdebug
899 G4cout<<"G4QKPElCS::GetExT: Q2="<<q2<<",r3="<<R2<<",b3="<<theB2<<",t3="<<ts2<<G4endl;
900#endif
901 }
902 else
903 {
904 G4double ran=R4*G4UniformRand();
905 if(ran>1.) ran=1.;
906 q2=-std::log(1.-ran)/theB4;
907 if(a<6.5) q2=lastTM-q2; // u reduced for lightA (starts from 0)
908#ifdef tdebug
909 G4cout<<"G4QKPElCS::GET:Q2="<<q2<<",m="<<lastTM<<",b4="<<theB3<<",t4="<<ts3<<G4endl;
910#endif
911 }
912 }
913 if(q2<0.) q2=0.;
914 if(!(q2>=-1.||q2<=1.)) G4cout<<"*NAN*G4QKaonPlusElasticCS::GetExchT: -t="<<q2<<G4endl;
915 if(q2>lastTM)
916 {
917#ifdef tdebug
918 G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GET:-t="<<q2<<">"<<lastTM<<G4endl;
919#endif
920 q2=lastTM;
921 }
922 return q2*GeVSQ;
923}
924
925// Returns B in independent units (MeV^-2) (all internal calculations are in GeV) see ExT
927{
928 static const G4double GeVSQ=gigaelectronvolt*gigaelectronvolt;
929#ifdef tdebug
930 G4cout<<"G4QKaonPlusECS::GetS:"<<onlyCS<<",Z="<<tgZ<<",N="<<tgN<<",PDG="<<PDG<<G4endl;
931#endif
932 if(onlyCS)G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetSl:onlCS=true"<<G4endl;
933 if(lastLP<-4.3) return 0.; // S-wave for p<14 MeV/c (kinE<.1MeV)
934 if(PDG != 321)
935 {
936 // G4cout<<"*Error*G4QKaonPlusElasticCrossSection::GetSlope: PDG="<<PDG<<", Z="<<tgZ
937 // <<", N="<<tgN<<", while it is defined only for PDG=321"<<G4endl;
938 // throw G4QException("G4QKaonPlusElasticCrossSection::GetSlope:Only K+ is implemented");
940 ed << "PDG = " << PDG << ", Z = " << tgZ << ", N = " << tgN
941 << ", while it is defined only for PDG=321 (K+)" << G4endl;
942 G4Exception("G4QKaonPlusElasticCrossSection::GetSlope()", "HAD_CHPS_0000",
943 FatalException, ed);
944 }
945 if(theB1<0.) theB1=0.;
946 if(!(theB1>=-1.||theB1<=1.))G4cout<<"*NAN*G4QKaonPlusElCS::GetSlope:B1="<<theB1<<G4endl;
947 return theB1/GeVSQ;
948}
949
950// Returns half max(Q2=-t) in independent units (MeV^2)
952{
953 static const G4double HGeVSQ=gigaelectronvolt*gigaelectronvolt/2.;
954 return lastTM*HGeVSQ;
955}
956
957// lastLP is used, so calculating tables, one need to remember and then recover lastLP
958G4double G4QKaonPlusElasticCrossSection::GetTabValues(G4double lp, G4int PDG, G4int tgZ,
959 G4int tgN)
960{
961 if(PDG!=321)G4cout<<"*Warning*G4QKaonPlusElasticCrossSection::GetTaV:PDG="<<PDG<<G4endl;
962 if(tgZ<0 || tgZ>92)
963 {
964 G4cout<<"*Warning*G4QKaonPlusElasticCS::GetTabV:(1-92)NoIsotopes for Z="<<tgZ<<G4endl;
965 return 0.;
966 }
967 G4int iZ=tgZ-1; // Z index
968 if(iZ<0)
969 {
970 iZ=0; // conversion of the neutron target to the proton target
971 tgZ=1;
972 tgN=0;
973 }
974 //if(nN[iZ][0] < 0)
975 //{
976#ifdef isodebug
977 // G4cout<<"*Warning*G4QKaonPlusElasticCS::GetTabVal:NoIsotopes for Z="<<tgZ<<G4endl;
978#endif
979 // return 0.;
980 //}
981#ifdef pdebug
982 G4cout<<"G4QKaonPlusECS::GetTV: l="<<lp<<",Z="<<tgZ<<",N="<<tgN<<",PDG="<<PDG<<G4endl;
983#endif
984 G4double p=std::exp(lp); // momentum
985 G4double sp=std::sqrt(p); // sqrt(p)
986 G4double p2=p*p;
987 G4double p3=p2*p;
988 G4double p4=p3*p;
989 if ( tgZ == 1 && tgN == 0 ) // KaonPlus+P
990 {
991 G4double dl2=lp-lastPAR[11];
992 theSS=lastPAR[34];
993 theS1=(lastPAR[12]+lastPAR[13]*dl2*dl2)/(1.+lastPAR[14]/p4/p)+
994 (lastPAR[15]/p2+lastPAR[16]*p)/(p4+lastPAR[17]*sp);
995 theB1=lastPAR[18]*std::pow(p,lastPAR[19])/(1.+lastPAR[20]/p3);
996 theS2=lastPAR[21]+lastPAR[22]/(p4+lastPAR[23]*p);
997 theB2=lastPAR[24]+lastPAR[25]/(p4+lastPAR[26]/sp);
998 theS3=lastPAR[27]+lastPAR[28]/(p4*p4+lastPAR[29]*p2+lastPAR[30]);
999 theB3=lastPAR[31]+lastPAR[32]/(p4+lastPAR[33]);
1000 theS4=0.;
1001 theB4=0.;
1002#ifdef tdebug
1003 G4cout<<"G4QKaonPlusElasticCrossSection::GetTabV:TM="<<lastTM<<",S1="<<theS1<<",B1="
1004 <<theB1<<",S2="<<theS2<<",B2="<<theB2<<",S3="<<theS1<<",B3="<<theB1<<G4endl;
1005#endif
1006 // Returns the total elastic pim-p cross-section (to avoid spoiling lastSIG)
1007 G4double dp=lp-lastPAR[4];
1008//G4cout<<"lastPAR[8] "<<lastPAR[8]<<" lastPAR[9] "<<lastPAR[9]<<" lastPAR[10] "<<lastPAR[10]<<G4endl;
1009 return lastPAR[0]/(lastPAR[2]+sqr(p-lastPAR[1]))+(lastPAR[3]*dp*dp+lastPAR[5])/
1010 (1.-lastPAR[6]/sp+lastPAR[7]/p4)
1011 +lastPAR[8]/(sqr(p-lastPAR[9])+lastPAR[10]); // Uzhi
1012
1013 }
1014 else
1015 {
1016 G4double p5=p4*p;
1017 G4double p6=p5*p;
1018 G4double p8=p6*p2;
1019 G4double p10=p8*p2;
1020 G4double p12=p10*p2;
1021 G4double p16=p8*p8;
1022 //G4double p24=p16*p8;
1023 G4double dl=lp-5.;
1024 G4double a=tgZ+tgN;
1025 G4double pah=std::pow(p,a/2);
1026 G4double pa=pah*pah;
1027 G4double pa2=pa*pa;
1028 if(a<6.5)
1029 {
1030 theS1=lastPAR[9]/(1.+lastPAR[10]*p4*pa)+lastPAR[11]/(p4+lastPAR[12]*p4/pa2)+
1031 (lastPAR[13]*dl*dl+lastPAR[14])/(1.+lastPAR[15]/p2);
1032 theB1=(lastPAR[16]+lastPAR[17]*p2)/(p4+lastPAR[18]/pah)+lastPAR[19];
1033 theSS=lastPAR[20]/(1.+lastPAR[21]/p2)+lastPAR[22]/(p6/pa+lastPAR[23]/p16);
1034 theS2=lastPAR[24]/(pa/p2+lastPAR[25]/p4)+lastPAR[26];
1035 theB2=lastPAR[27]*std::pow(p,lastPAR[28])+lastPAR[29]/(p8+lastPAR[30]/p16);
1036 theS3=lastPAR[31]/(pa*p+lastPAR[32]/pa)+lastPAR[33];
1037 theB3=lastPAR[34]/(p3+lastPAR[35]/p6)+lastPAR[36]/(1.+lastPAR[37]/p2);
1038 theS4=p2*(pah*lastPAR[38]*std::exp(-pah*lastPAR[39])+
1039 lastPAR[40]/(1.+lastPAR[41]*std::pow(p,lastPAR[42])));
1040 theB4=lastPAR[43]*pa/p2/(1.+pa*lastPAR[44]);
1041#ifdef tdebug
1042 G4cout<<"G4QKaonPlusElasticCS::GetTabV: lA, p="<<p<<",S1="<<theS1<<",B1="<<theB1
1043 <<",SS="<<theSS<<",S2="<<theS2<<",B2="<<theB2<<",S3="<<theS3<<",B3="<<theB3
1044 <<",S4="<<theS4<<",B4="<<theB4<<G4endl;
1045#endif
1046 }
1047 else
1048 {
1049 theS1=lastPAR[9]/(1.+lastPAR[10]/p4)+lastPAR[11]/(p4+lastPAR[12]/p2)+
1050 lastPAR[13]/(p5+lastPAR[14]/p16);
1051 theB1=(lastPAR[15]/p8+lastPAR[19])/(p+lastPAR[16]/std::pow(p,lastPAR[20]))+
1052 lastPAR[17]/(1.+lastPAR[18]/p4);
1053 theSS=lastPAR[21]/(p4/std::pow(p,lastPAR[23])+lastPAR[22]/p4);
1054 theS2=lastPAR[24]/p4/(std::pow(p,lastPAR[25])+lastPAR[26]/p12)+lastPAR[27];
1055 theB2=lastPAR[28]/std::pow(p,lastPAR[29])+lastPAR[30]/std::pow(p,lastPAR[31]);
1056 theS3=lastPAR[32]/std::pow(p,lastPAR[35])/(1.+lastPAR[36]/p12)+
1057 lastPAR[33]/(1.+lastPAR[34]/p6);
1058 theB3=lastPAR[37]/p8+lastPAR[38]/p2+lastPAR[39]/(1.+lastPAR[40]/p8);
1059 theS4=(lastPAR[41]/p4+lastPAR[46]/p)/(1.+lastPAR[42]/p10)+
1060 (lastPAR[43]+lastPAR[44]*dl*dl)/(1.+lastPAR[45]/p12);
1061 theB4=lastPAR[47]/(1.+lastPAR[48]/p)+lastPAR[49]*p4/(1.+lastPAR[50]*p5);
1062#ifdef tdebug
1063 G4cout<<"G4QKaonPlusElasticCS::GetTabVal:hA,p="<<p<<",S1="<<theS1<<",B1="<<theB1
1064 <<",SS="<<theSS<<",S2="<<theS2<<",B2="<<theB2<<",S3="<<theS3<<",B3="<<theB3
1065 <<",S4="<<theS4<<",B4="<<theB4<<G4endl;
1066#endif
1067 }
1068 // Returns the total elastic (n/p)A cross-section (to avoid spoiling lastSIG)
1069#ifdef tdebug
1070 G4cout<<"G4QKaonPlusElCS::GTV: PDG="<<PDG<<",P="<<p<<",N="<<tgN<<",Z="<<tgZ<<G4endl;
1071#endif
1072 G4double dlp=lp-lastPAR[4]; // ax
1073 // p1 p2 p3 p4
1074 return (lastPAR[0]*dlp*dlp+lastPAR[1]+lastPAR[2]/p2)/(1.+lastPAR[3]/p2/sp);
1075 }
1076 return 0.;
1077} // End of GetTableValues
1078
1079// Returns max -t=Q2 (GeV^2) for the momentum pP(GeV) and the target nucleus (tgN,tgZ)
1080G4double G4QKaonPlusElasticCrossSection::GetQ2max(G4int PDG, G4int tgZ, G4int tgN,
1081 G4double pP)
1082{
1083 //static const G4double mNeut= G4QPDGCode(2112).GetMass()*.001; // MeV to GeV
1084 //static const G4double mPi= G4QPDGCode(211).GetMass()*.001; // pion mass MeV to GeV
1085 static const G4double mK= G4QPDGCode(321).GetMass()*.001; // kaon mass MeV to GeV
1086 //static const G4double mProt= G4QPDGCode(2212).GetMass()*.001; // MeV to GeV
1087 //static const G4double mLamb= G4QPDGCode(3122).GetMass()*.001; // MeV to GeV
1088 //static const G4double mHe3 = G4QPDGCode(2112).GetNuclMass(2,1,0)*.001; // MeV to GeV
1089 //static const G4double mAlph = G4QPDGCode(2112).GetNuclMass(2,2,0)*.001; // MeV to GeV
1090 //static const G4double mDeut = G4QPDGCode(2112).GetNuclMass(1,1,0)*.001; // MeV to GeV
1091 static const G4double mK2= mK*mK;
1092 //static const G4double mPi2= mPi*mPi;
1093 //static const G4double mProt2= mProt*mProt;
1094 //static const G4double mNeut2= mNeut*mNeut;
1095 //static const G4double mDeut2= mDeut*mDeut;
1096 G4double pP2=pP*pP; // squared momentum of the projectile
1097 if(tgZ || tgN>-1) // ---> pipA
1098 {
1099 G4double mt=G4QPDGCode(90000000+tgZ*1000+tgN).GetMass()*.001; // Target mass in GeV
1100 G4double dmt=mt+mt;
1101 G4double s_value=dmt*std::sqrt(pP2+mK2)+mK2+mt*mt; // Mondelstam s
1102 return dmt*dmt*pP2/s_value;
1103 }
1104 else
1105 {
1106 // G4cout<<"*Error*G4QKaonPlusElasticCrossSection::GetQ2m:PDG="<<PDG<<",Z="<<tgZ<<",N="
1107 // <<tgN<<", while it is defined only for p projectiles & Z_target>0"<<G4endl;
1108 // throw G4QException("G4QKaonPlusElasticCrossSection::GetQ2max:only K+ is implemented");
1110 ed << "PDG = " << PDG << ",Z = " << tgZ << ", N = " << tgN
1111 << ", while it is defined only for p projectiles & Z_target>0" << G4endl;
1112 G4Exception("G4QKaonPlusElasticCrossSection::GetQ2max()", "HAD_CHPS_0000",
1113 FatalException, ed);
1114 return 0;
1115 }
1116}
@ FatalException
double G4double
Definition: G4Types.hh:64
int G4int
Definition: G4Types.hh:66
bool G4bool
Definition: G4Types.hh:67
#define G4endl
Definition: G4ios.hh:52
G4DLLIMPORT std::ostream G4cout
#define G4UniformRand()
Definition: Randomize.hh:53
virtual G4double GetCrossSection(G4bool fCS, G4double pMom, G4int tgZ, G4int tgN, G4int pPDG=321)
G4double GetSlope(G4int tZ, G4int tN, G4int pPDG)
G4double GetExchangeT(G4int tZ, G4int tN, G4int pPDG)
G4double CalculateCrossSection(G4bool CS, G4int F, G4int I, G4int pPDG, G4int Z, G4int N, G4double pP)
G4double GetMass()
Definition: G4QPDGCode.cc:693
virtual G4double ThresholdEnergy(G4int Z, G4int N, G4int PDG=0)
void G4Exception(const char *originOfException, const char *exceptionCode, G4ExceptionSeverity severity, const char *comments)
Definition: G4Exception.cc:41
std::ostringstream G4ExceptionDescription
Definition: globals.hh:76
T sqr(const T &x)
Definition: templates.hh:145