CbmRoot
Loading...
Searching...
No Matches
CbmLitMaterialEffectsImp.cxx
Go to the documentation of this file.
1/* Copyright (C) 2008-2023 GSI/JINR-LIT, Darmstadt/Dubna
2 SPDX-License-Identifier: GPL-3.0-only
3 Authors: Andrey Lebedev [committer], Martin Beyer */
4
11
15
16#include <TDatabasePDG.h>
17#include <TParticlePDG.h>
18
19#include <cassert>
20#include <cmath>
21#include <cstdlib>
22#include <iostream>
23
25 : fMass(0.105)
26 , fDownstream(true)
27 , fIsElectron(false)
28 , fIsMuon(true)
29{
30}
31
33
35 bool downstream)
36{
37 if (mat->GetLength() * mat->GetRho() < 1e-10) {
38 return kLITSUCCESS;
39 }
40
41 fDownstream = downstream;
42 TDatabasePDG* db = TDatabasePDG::Instance();
43 TParticlePDG* particle = db->GetParticle(pdg);
44 assert(particle != nullptr);
45 fMass = particle->Mass();
46 fIsElectron = (std::abs(pdg) == 11) ? true : false;
47 fIsMuon = (std::abs(pdg) == 13) ? true : false;
48
49 AddEnergyLoss(par, mat);
50
51 // AddThinScatter(par, mat);
52 AddThickScatter(par, mat);
53
54 return kLITSUCCESS;
55}
56
58{
59 litfloat Eloss = EnergyLoss(par, mat);
60 par->SetQp(CalcQpAfterEloss(par->GetQp(), Eloss));
61
62 litfloat cov = par->GetCovariance(18);
63 cov += CalcSigmaSqQp(par, mat); // FIXME: Full bethe bloch is used even if energy loss is BetheBlochElectron
64 par->SetCovariance(18, cov);
65}
66
68{
69 if (mat->GetLength() < 1e-10) {
70 return;
71 }
72 litfloat tx = par->GetTx();
73 litfloat ty = par->GetTy();
74 litfloat thickness = mat->GetLength(); //cm
75 litfloat thetaSq = CalcThetaSq(par, mat);
76
77 litfloat t = 1 + tx * tx + ty * ty;
78
79 litfloat Q33 = (1 + tx * tx) * t * thetaSq;
80 litfloat Q44 = (1 + ty * ty) * t * thetaSq;
81 litfloat Q34 = tx * ty * t * thetaSq;
82
83 litfloat T23 = (thickness * thickness) / 3.0;
84 litfloat T2 = thickness / 2.0;
85
86 litfloat D = (fDownstream) ? 1. : -1.;
87
88 std::vector<litfloat> C = par->GetCovMatrix();
89
90 C[0] += Q33 * T23;
91 C[1] += Q34 * T23;
92 C[2] += Q33 * D * T2;
93 C[3] += Q34 * D * T2;
94
95 C[6] += Q44 * T23;
96 C[7] += Q34 * D * T2;
97 C[8] += Q44 * D * T2;
98
99 C[11] += Q33;
100 C[12] += Q34;
101
102 C[15] += Q44;
103
104 par->SetCovMatrix(C);
105}
106
108{
109 if (mat->GetLength() < 1e-10) {
110 return;
111 }
112 litfloat tx = par->GetTx();
113 litfloat ty = par->GetTy();
114 litfloat thetaSq = CalcThetaSq(par, mat);
115
116 litfloat t = 1 + tx * tx + ty * ty;
117
118 litfloat Q33 = (1 + tx * tx) * t * thetaSq;
119 litfloat Q44 = (1 + ty * ty) * t * thetaSq;
120 litfloat Q34 = tx * ty * t * thetaSq;
121
122 std::vector<litfloat> C = par->GetCovMatrix();
123 C[11] += Q33;
124 C[15] += Q44;
125 C[12] += Q34;
126 par->SetCovMatrix(C);
127}
128
130{
131 litfloat p = std::abs(1. / par->GetQp()); //GeV
132 litfloat E = std::sqrt(fMass * fMass + p * p);
133 litfloat beta = p / E;
134 litfloat x = mat->GetLength(); //cm
135 litfloat X0 = mat->GetRL(); //cm
136 litfloat bcp = beta * p;
137 litfloat z = 1.;
138
139 litfloat theta = 0.0136 * (1. / bcp) * z * std::sqrt(x / X0) * (1. + 0.038 * std::log(x / X0));
140 return theta * theta;
141}
142
144{
145 litfloat length = mat->GetRho() * mat->GetLength();
146 return dEdx(par, mat) * length;
147 //return MPVEnergyLoss(par, mat);
148}
149
151{
152 litfloat dedx = fIsElectron ? BetheBlochElectron(par, mat) : BetheBloch(par, mat);
153 // dedx += BetheHeitler(par, mat);
154 // if (fIsMuon) dedx += PairProduction(par, mat);
155 return dedx;
156}
157
159{
160 litfloat K = 0.000307075; // GeV * mol^-1 * cm^2
161 litfloat z = (par->GetQp() > 0.) ? 1 : -1.;
162 litfloat Z = mat->GetZ(); // no unit
163 litfloat A = mat->GetA(); // g * mol^-1
164
165 litfloat M = fMass;
166 litfloat p = std::abs(1. / par->GetQp()); //GeV
167 litfloat E = std::sqrt(M * M + p * p);
168 litfloat beta = p / E;
169 litfloat betaSq = beta * beta;
170 litfloat gamma = E / M;
171 litfloat gammaSq = gamma * gamma;
172
173 litfloat I = CalcI(Z) * 1e-9; // GeV
174
175 litfloat me = 0.000511; // GeV
176 litfloat ratio = me / M;
177 litfloat Tmax = (2 * me * betaSq * gammaSq) / (1 + 2 * gamma * ratio + ratio * ratio);
178
179 // density correction
180 litfloat dc = 0.;
181 if (p > 0.5) { // for particles above 1 Gev
182 litfloat rho = mat->GetRho();
183 litfloat hwp = 28.816 * std::sqrt(rho * Z / A) * 1e-9; // GeV
184 dc = std::log(hwp / I) + std::log(beta * gamma) - 0.5;
185 }
186
187 return K * z * z * (Z / A) * (1. / betaSq)
188 * (0.5 * std::log(2 * me * betaSq * gammaSq * Tmax / (I * I)) - betaSq - dc);
189}
190
192{
193 litfloat K = 0.000307075; // GeV * mol^-1 * cm^2
194 litfloat Z = mat->GetZ(); // no unit
195 litfloat A = mat->GetA(); // g * mol^-1
196
197 litfloat me = 0.000511; // GeV;
198 litfloat p = std::abs(1. / par->GetQp()); //GeV
199 litfloat E = std::sqrt(me * me + p * p);
200 litfloat gamma = E / me;
201
202 litfloat I = CalcI(Z) * 1e-9; // GeV
203
204 // TODO: check this, since such a asymmetry is not seen in geant3 or geant4
205 // different energy loss should only be relevant for low momentum < 100 MeV
206 // For now only use the 2. equation, since it matches geant3 and geant4 better
207 if (false) { // electrons
208 return K * (Z / A) * (std::log(2 * me / I) + 1.5 * std::log(gamma) - 0.975);
209 }
210 else { // positrons
211 return K * (Z / A) * (std::log(2 * me / I) + 2. * std::log(gamma) - 1.);
212 }
213}
214
216{
217 litfloat massSq = fMass * fMass;
218 litfloat p = std::abs(1. / qp);
219 litfloat E = std::sqrt(p * p + massSq);
220 litfloat q = (qp > 0) ? 1. : -1.;
221 if (!fDownstream) {
222 eloss *= -1.0;
223 } // TODO check this
224 litfloat Enew = E - eloss;
225 litfloat pnew = (Enew > fMass) ? std::sqrt(Enew * Enew - massSq) : 0.;
226 if (pnew != 0) {
227 return q / pnew;
228 }
229 else {
230 return 1e5;
231 }
232
233 //if (!fDownstream) eloss *= -1.0;
234 //if (p > 0.) p -= eloss;
235 //else p += eloss;
236 //return 1./p;
237}
238
240{
241 litfloat P = std::abs(1. / par->GetQp()); // GeV
242 litfloat XMASS = fMass; // GeV
243 litfloat E = std::sqrt(P * P + XMASS * XMASS);
244 litfloat Z = mat->GetZ();
245 litfloat A = mat->GetA();
246 litfloat RHO = mat->GetRho();
247 litfloat STEP = mat->GetLength();
248 litfloat EMASS = 0.511 * 1e-3; // GeV
249
250 litfloat BETA = P / E;
251 litfloat GAMMA = E / XMASS;
252
253 // Calculate xi factor (KeV).
254 litfloat XI = (153.5 * Z * STEP * RHO) / (A * BETA * BETA);
255
256 // Maximum energy transfer to atomic electron (KeV).
257 litfloat ETA = BETA * GAMMA;
258 litfloat ETASQ = ETA * ETA;
259 litfloat RATIO = EMASS / XMASS;
260 litfloat F1 = 2. * EMASS * ETASQ;
261 litfloat F2 = 1. + 2. * RATIO * GAMMA + RATIO * RATIO;
262 litfloat EMAX = 1e6 * F1 / F2;
263
264 litfloat DEDX2 = XI * EMAX * (1. - (BETA * BETA / 2.)) * 1e-12;
265
266 litfloat SDEDX = (E * E * DEDX2) / std::pow(P, 6);
267
268 return std::abs(SDEDX);
269}
270
272 const CbmLitMaterialInfo* mat) const
273{
274 litfloat x = mat->GetLength(); //cm
275 litfloat X0 = mat->GetRL(); //cm
276 return par->GetQp() * par->GetQp() * (std::exp(-x / X0 * std::log(3.0) / std::log(2.0)) - std::exp(-2.0 * x / X0));
277}
278
280{
281 // mean excitation energy in eV
282 if (Z > 16.) {
283 return 10 * Z;
284 }
285 else {
286 return 16 * std::pow(Z, 0.9);
287 }
288}
289
291{
292 litfloat M = fMass; //GeV
293 litfloat p = std::abs(1. / par->GetQp()); // GeV
294 litfloat rho = mat->GetRho();
295 litfloat X0 = mat->GetRL();
296 litfloat me = 0.000511; // GeV
297 litfloat E = std::sqrt(M * M + p * p);
298 litfloat ratio = me / M;
299
300 return (E * ratio * ratio) / (X0 * rho);
301}
302
304{
305 litfloat p = std::abs(1. / par->GetQp()); // GeV
306 litfloat M = fMass; //GeV
307 litfloat rho = mat->GetRho();
308 litfloat X0 = mat->GetRL();
309 litfloat E = std::sqrt(M * M + p * p);
310
311 return 7e-5 * E / (X0 * rho);
312}
313
318
320{
321 litfloat M = fMass * 1e3; //MeV
322 litfloat p = std::abs(1. / par->GetQp()) * 1e3; // MeV
323
324 // myf rho = mat->GetRho();
325 litfloat Z = mat->GetZ();
326 litfloat A = mat->GetA();
327 litfloat x = mat->GetRho() * mat->GetLength();
328
329 litfloat I = CalcI(Z) * 1e-6; // MeV
330
331 litfloat K = 0.307075; // MeV g^-1 cm^2
332 litfloat j = 0.200;
333
334 litfloat E = std::sqrt(M * M + p * p);
335 litfloat beta = p / E;
336 litfloat betaSq = beta * beta;
337 litfloat gamma = E / M;
338 litfloat gammaSq = gamma * gamma;
339
340 litfloat ksi = (K / 2.) * (Z / A) * (x / betaSq); // MeV
341
342 // myf hwp = 28.816 * std::sqrt(rho*Z/A) * 1e-6 ; // MeV
343 // myf dc = std::log(hwp/I) + std::log(beta*gamma) - 0.5;
344 // dc *= 2;
345 litfloat dc = 0.;
346
347 litfloat eloss = ksi * (std::log(2 * M * betaSq * gammaSq / I) + std::log(ksi / I) + j - betaSq - dc);
348
349 return eloss * 1e-3; //GeV
350}
LitStatus
Definition CbmLitEnums.h:29
@ kLITSUCCESS
Definition CbmLitEnums.h:30
double litfloat
Definition CbmLitFloat.h:19
Calculation of multiple scattering and energy loss.
Data class for track parameters.
litfloat CalcThetaSq(const CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
LitStatus Update(CbmLitTrackParam *par, const CbmLitMaterialInfo *mat, int pdg, bool downstream)
Inherited from CbmLitMaterialEffects.
litfloat CalcI(litfloat Z) const
void AddEnergyLoss(CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
litfloat BetheBlochElectron(const CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
litfloat BetheHeitler(const CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
litfloat dEdx(const CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
litfloat MPVEnergyLoss(const CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
litfloat CalcSigmaSqQpElectron(const CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
void AddThickScatter(CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
void AddThinScatter(CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
virtual ~CbmLitMaterialEffectsImp()
Destructor.
litfloat CalcQpAfterEloss(litfloat qp, litfloat eloss) const
litfloat PairProduction(const CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
litfloat BetheBloch(const CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
litfloat CalcSigmaSqQp(const CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
litfloat BetheBlochSimple(const CbmLitMaterialInfo *mat) const
litfloat EnergyLoss(const CbmLitTrackParam *par, const CbmLitMaterialInfo *mat) const
litfloat GetLength() const
litfloat GetRL() const
litfloat GetRho() const
litfloat GetZ() const
litfloat GetA() const
Data class for track parameters.
litfloat GetTx() const
void SetQp(litfloat qp)
void SetCovariance(int index, litfloat cov)
litfloat GetTy() const
const vector< litfloat > & GetCovMatrix() const
void SetCovMatrix(const vector< litfloat > &C)
litfloat GetCovariance(int index) const
litfloat GetQp() const
static const litfloat ENERGY_LOSS_CONST