Geant4 11.1.1
Toolkit for the simulation of the passage of particles through matter
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
G4UCNMaterialPropertiesTable.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//
28//
29//....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
30//
31// G4UCNMaterialPropertiesTable
32// ----------------------------
33//
34// Derives from G4MaterialPropertiesTable and adds a double pointer to the
35// MicroRoughnessTable
36//
37// This file includes the initialization and calculation of the mr-lookup
38// tables. It also provides the functions to read from these tables and to
39// calculate the probability for certain angles.
40//
41// For a closer description see the header file
42//
43//....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
44
45#include <fstream>
46
49
50#include "G4SystemOfUnits.hh"
52
55{
56 theMicroRoughnessTable = nullptr;
57 maxMicroRoughnessTable = nullptr;
58 theMicroRoughnessTransTable = nullptr;
59 maxMicroRoughnessTransTable = nullptr;
60
61 theta_i_min = 0.*degree;
62 theta_i_max = 90.*degree;
63
64 Emin = 0.e-9*eV;
65 Emax = 1000.e-9*eV;
66
67 no_theta_i = 90;
68 noE = 100;
69
70 theta_i_step = (theta_i_max-theta_i_min)/(no_theta_i-1);
71 E_step = (Emax-Emin)/(noE-1);
72
73 b = 1*nm;
74 w = 30*nm;
75
76 AngCut = 0.01*degree;
77}
78
80{
81 delete theMicroRoughnessTable;
82 delete maxMicroRoughnessTable;
83 delete theMicroRoughnessTransTable;
84 delete maxMicroRoughnessTransTable;
85}
86
88{
89 return theMicroRoughnessTable;
90}
91
93{
94 return theMicroRoughnessTransTable;
95}
96
98 LoadMicroRoughnessTables(G4double* pMicroRoughnessTable,
99 G4double* pmaxMicroRoughnessTable,
100 G4double* pMicroRoughnessTransTable,
101 G4double* pmaxMicroRoughnessTransTable)
102{
103 theMicroRoughnessTable = pMicroRoughnessTable;
104 maxMicroRoughnessTable = pmaxMicroRoughnessTable;
105 theMicroRoughnessTransTable = pMicroRoughnessTransTable;
106 maxMicroRoughnessTransTable = pmaxMicroRoughnessTransTable;
107}
108
110{
111 G4int NEdim = 0;
112 G4int Nthetadim = 0;
113
114 // Checks if the number of angles is available and stores it
115
116 if(ConstPropertyExists("MR_NBTHETA"))
117 {
118 Nthetadim = G4int(GetConstProperty("MR_NBTHETA") + 0.1);
119 }
120
121 // Checks if the number of energies is available and stores it
122
123 if(ConstPropertyExists("MR_NBE"))
124 {
125 NEdim = G4int(GetConstProperty("MR_NBE") + 0.1);
126 }
127
128 //G4cout << "thetadim: " << Nthetadim << " , Edim: " << NEdim << G4endl;
129
130 // If both dimensions of the lookup-table are non-trivial:
131 // delete old tables if existing and allocate memory for new tables
132
133 if (Nthetadim*NEdim > 0) {
134 delete theMicroRoughnessTable;
135 theMicroRoughnessTable = new G4double[Nthetadim * NEdim];
136 delete maxMicroRoughnessTable;
137 maxMicroRoughnessTable = new G4double[Nthetadim * NEdim];
138 delete theMicroRoughnessTransTable;
139 theMicroRoughnessTransTable = new G4double[Nthetadim * NEdim];
140 delete maxMicroRoughnessTransTable;
141 maxMicroRoughnessTransTable = new G4double[Nthetadim * NEdim];
142 }
143}
144
146{
147// Reads the parameters for the mr-probability computation from the
148// corresponding material properties and stores it in the appropriate
149// variables
150
151 b = GetConstProperty("MR_RRMS");
152 G4double b2 = b*b;
153 w = GetConstProperty("MR_CORRLEN");
154 G4double w2 = w*w;
155
156 no_theta_i = G4int(GetConstProperty("MR_NBTHETA")+0.1);
157 //G4cout << "no_theta: " << no_theta_i << G4endl;
158 noE = G4int(GetConstProperty("MR_NBE")+0.1);
159 //G4cout << "noE: " << noE << G4endl;
160
161 theta_i_min = GetConstProperty("MR_THETAMIN");
162 theta_i_max = GetConstProperty("MR_THETAMAX");
163 Emin = GetConstProperty("MR_EMIN");
164 Emax = GetConstProperty("MR_EMAX");
165 G4int AngNoTheta = G4int(GetConstProperty("MR_ANGNOTHETA")+0.1);
166 G4int AngNoPhi = G4int(GetConstProperty("MR_ANGNOPHI")+0.1);
167 AngCut = GetConstProperty("MR_ANGCUT");
168
169 // The Fermi potential was saved in neV by P.F.
170
171 G4double fermipot = GetConstProperty("FERMIPOT")*(1.e-9*eV);
172
173 //G4cout << "Fermipot: " << fermipot/(1.e-9*eV) << "neV" << G4endl;
174
175 G4double theta_i, E;
176
177 // Calculates the increment in theta_i in the lookup-table
178 theta_i_step = (theta_i_max-theta_i_min)/(no_theta_i-1);
179
180 //G4cout << "theta_i_step: " << theta_i_step << G4endl;
181
182 // Calculates the increment in energy in the lookup-table
183 E_step = (Emax-Emin)/(noE-1);
184
185 // Runs the lookup-table memory allocation
187
188 G4int counter = 0;
189
190 //G4cout << "Calculating Microroughnesstables...";
191
192 // Writes the mr-lookup-tables to files for immediate control
193
194 std::ofstream dateir("MRrefl.dat",std::ios::out);
195 std::ofstream dateit("MRtrans.dat",std::ios::out);
196
197 //G4cout << theMicroRoughnessTable << G4endl;
198
199 for (theta_i=theta_i_min; theta_i<=theta_i_max+1e-6; theta_i+=theta_i_step) {
200 // Calculation for each cell in the lookup-table
201 for (E=Emin; E<=Emax; E+=E_step) {
202 *(theMicroRoughnessTable+counter) =
204 IntIplus(E, fermipot, theta_i, AngNoTheta, AngNoPhi,
205 b2, w2, maxMicroRoughnessTable+counter, AngCut);
206
207 *(theMicroRoughnessTransTable+counter) =
209 IntIminus(E, fermipot, theta_i, AngNoTheta, AngNoPhi,
210 b2, w2, maxMicroRoughnessTransTable+counter,
211 AngCut);
212
213 dateir << *(theMicroRoughnessTable+counter) << G4endl;
214 dateit << *(theMicroRoughnessTransTable+counter) << G4endl;
215
216 counter++;
217
218 //G4cout << counter << G4endl;
219 }
220 }
221
222 dateir.close();
223 dateit.close();
224
225 // Writes the mr-lookup-tables to files for immediate control
226
227 std::ofstream dateic("MRcheck.dat",std::ios::out);
228 std::ofstream dateimr("MRmaxrefl.dat",std::ios::out);
229 std::ofstream dateimt("MRmaxtrans.dat",std::ios::out);
230
231 for (theta_i=theta_i_min; theta_i<=theta_i_max+1e-6; theta_i+=theta_i_step) {
232 for (E=Emin; E<=Emax; E+=E_step) {
233
234 // tests the GetXXProbability functions by writing the entries
235 // of the lookup tables to files
236
237 dateic << GetMRIntProbability(theta_i,E) << G4endl;
238 dateimr << GetMRMaxProbability(theta_i,E) << G4endl;
239 dateimt << GetMRMaxTransProbability(theta_i,E) << G4endl;
240 }
241 }
242
243 dateic.close();
244 dateimr.close();
245 dateimt.close();
246}
247
250{
251 if(theMicroRoughnessTable == nullptr)
252 {
253 G4cout << "Do not have theMicroRoughnessTable" << G4endl;
254 return 0.;
255 }
256
257 // if theta_i or energy outside the range for which the lookup table is
258 // calculated, the probability is set to zero
259
260 //G4cout << "theta_i: " << theta_i/degree << "degree"
261 // << " theta_i_min: " << theta_i_min/degree << "degree"
262 // << " theta_i_max: " << theta_i_max/degree << "degree"
263 // << " Energy: " << Energy/(1.e-9*eV) << "neV"
264 // << " Emin: " << Emin/(1.e-9*eV) << "neV"
265 // << " Emax: " << Emax/(1.e-9*eV) << "neV" << G4endl;
266
267 if(theta_i < theta_i_min || theta_i > theta_i_max || Energy < Emin ||
268 Energy > Emax)
269 {
270 return 0.;
271 }
272
273 // Determines the nearest cell in the lookup table which contains
274 // the probability
275
276 G4int theta_i_pos = G4int((theta_i-theta_i_min)/theta_i_step+0.5);
277 G4int E_pos = G4int((Energy-Emin)/E_step+0.5);
278
279 // lookup table is onedimensional (1 row), energy is in rows,
280 // theta_i in columns
281
282 //G4cout << "E_pos: " << E_pos << " theta_i_pos: " << theta_i_pos << G4endl;
283 //G4cout << "Probability: " << *(theMicroRoughnessTable+E_pos+theta_i_pos*(noE-1)) << G4endl;
284
285 return *(theMicroRoughnessTable+E_pos+theta_i_pos*(noE - 1));
286}
287
290{
291 if(theMicroRoughnessTransTable == nullptr)
292 {
293 return 0.;
294 }
295
296 // if theta_i or energy outside the range for which the lookup table
297 // is calculated, the probability is set to zero
298
299 if(theta_i < theta_i_min || theta_i > theta_i_max || Energy < Emin ||
300 Energy > Emax)
301 {
302 return 0.;
303 }
304
305 // Determines the nearest cell in the lookup table which contains
306 // the probability
307
308 G4int theta_i_pos = G4int((theta_i-theta_i_min)/theta_i_step+0.5);
309 G4int E_pos = G4int((Energy-Emin)/E_step+0.5);
310
311 // lookup table is onedimensional (1 row), energy is in rows,
312 // theta_i in columns
313
314 return *(theMicroRoughnessTransTable+E_pos+theta_i_pos*(noE - 1));
315}
316
319{
320 if(maxMicroRoughnessTable == nullptr)
321 {
322 return 0.;
323 }
324
325 // if theta_i or energy outside the range for which the lookup table
326 // is calculated, the probability is set to zero
327
328 if(theta_i < theta_i_min || theta_i > theta_i_max || Energy < Emin ||
329 Energy > Emax)
330 {
331 return 0.;
332 }
333
334 // Determines the nearest cell in the lookup table which contains
335 // the probability
336
337 G4int theta_i_pos = G4int((theta_i-theta_i_min)/theta_i_step+0.5);
338 G4int E_pos = G4int((Energy-Emin)/E_step+0.5);
339
340 // lookup table is onedimensional (1 row), energy is in rows,
341 // theta_i in columns
342
343 return *(maxMicroRoughnessTable+E_pos+theta_i_pos*noE);
344}
345
347 SetMRMaxProbability(G4double theta_i, G4double Energy, G4double value)
348{
349 if(maxMicroRoughnessTable != nullptr)
350 {
351 if(theta_i < theta_i_min || theta_i > theta_i_max || Energy < Emin ||
352 Energy > Emax)
353 {}
354 else
355 {
356 // Determines the nearest cell in the lookup table which contains
357 // the probability
358
359 G4int theta_i_pos = G4int((theta_i - theta_i_min) / theta_i_step + 0.5);
360 G4int E_pos = G4int((Energy - Emin) / E_step + 0.5);
361
362 // lookup table is onedimensional (1 row), energy is in rows,
363 // theta_i in columns
364
365 *(maxMicroRoughnessTable + E_pos + theta_i_pos * noE) = value;
366 }
367 }
368}
369
372{
373 if(maxMicroRoughnessTransTable == nullptr)
374 {
375 return 0.;
376 }
377
378 // if theta_i or energy outside the range for which the lookup table
379 // is calculated, the probability is set to zero
380
381 if(theta_i < theta_i_min || theta_i > theta_i_max || Energy < Emin ||
382 Energy > Emax)
383 {
384 return 0.;
385 }
386
387 // Determines the nearest cell in the lookup table which contains
388 // the probability
389
390 G4int theta_i_pos = G4int((theta_i-theta_i_min)/theta_i_step+0.5);
391 G4int E_pos = G4int((Energy-Emin)/E_step+0.5);
392
393 // lookup table is onedimensional (1 row), energy is in rows,
394 // theta_i in columns
395
396 return *(maxMicroRoughnessTransTable+E_pos+theta_i_pos*noE);
397}
398
401{
402 if(maxMicroRoughnessTransTable != nullptr)
403 {
404 if(theta_i < theta_i_min || theta_i > theta_i_max || Energy < Emin ||
405 Energy > Emax)
406 {}
407 else
408 {
409 // Determines the nearest cell in the lookup table which contains
410 // the probability
411
412 G4int theta_i_pos = G4int((theta_i - theta_i_min) / theta_i_step + 0.5);
413 G4int E_pos = G4int((Energy - Emin) / E_step + 0.5);
414
415 // lookup table is onedimensional (1 row), energy is in rows,
416 // theta_i in columns
417
418 *(maxMicroRoughnessTransTable + E_pos + theta_i_pos * noE) = value;
419 }
420 }
421}
422
424 GetMRProbability(G4double theta_i, G4double Energy,
425 G4double fermipot,
426 G4double theta_o, G4double phi_o)
427{
429 ProbIplus(Energy, fermipot, theta_i, theta_o, phi_o, b, w, AngCut);
430}
431
434 G4double fermipot,
435 G4double theta_o, G4double phi_o)
436{
438 ProbIminus(Energy, fermipot,theta_i, theta_o, phi_o, b, w, AngCut);
439}
440
442 G4double VFermi,
443 G4double theta_i)
444{
445 G4double k = std::sqrt(2*neutron_mass_c2*E / hbarc_squared);
446 G4double k_l = std::sqrt(2*neutron_mass_c2*VFermi / hbarc_squared);
447
448 //G4cout << " Energy: " << E/(1.e-9*eV) << "neV"
449 // << " VFermi: " << VFermi/(1.e-9*eV) << "neV"
450 // << " theta: " << theta_i/degree << "degree" << G4endl;
451
452 //G4cout << " Conditions - 2*b*k*cos(theta): " << 2*b*k*cos(theta_i)
453 // << ", 2*b*kl: " << 2*b*k_l << G4endl;
454
455 // see eq. 17 of the Steyerl paper
456
457 return 2 * b * k * std::cos(theta_i) < 1 && 2 * b * k_l < 1;
458}
459
461 G4double VFermi,
462 G4double theta_i)
463{
464 G4double k2 = 2*neutron_mass_c2*E / hbarc_squared;
465 G4double k_l2 = 2*neutron_mass_c2*VFermi / hbarc_squared;
466
467 if(E * (std::cos(theta_i) * std::cos(theta_i)) < VFermi)
468 {
469 return false;
470 }
471
472 G4double kS2 = k_l2 - k2;
473
474 //G4cout << "Conditions; 2bk' cos(theta): " << 2*b*sqrt(kS2)*cos(theta_i) <<
475 // ", 2bk_l: " << 2*b*sqrt(k_l2) << G4endl;
476
477 // see eq. 18 of the Steyerl paper
478
479 return 2 * b * std::sqrt(kS2) * std::cos(theta_i) < 1 &&
480 2 * b * std::sqrt(k_l2) < 1;
481}
482
485 G4int no_theta, G4int no_E,
486 G4double theta_min, G4double theta_max,
487 G4double E_min, G4double E_max,
488 G4int AngNoTheta, G4int AngNoPhi,
489 G4double AngularCut)
490{
491 //G4cout << "Setting Microroughness Parameters...";
492
493 // Removes an existing RMS roughness
494 if(ConstPropertyExists("MR_RRMS"))
495 {
496 RemoveConstProperty("MR_RRMS");
497 }
498
499 // Adds a new RMS roughness
500 AddConstProperty("MR_RRMS", bb);
501
502 //G4cout << "b: " << bb << G4endl;
503
504 // Removes an existing correlation length
505 if(ConstPropertyExists("MR_CORRLEN"))
506 {
507 RemoveConstProperty("MR_CORRLEN");
508 }
509
510 // Adds a new correlation length
511 AddConstProperty("MR_CORRLEN", ww);
512
513 //G4cout << "w: " << ww << G4endl;
514
515 // Removes an existing number of thetas
516 if(ConstPropertyExists("MR_NBTHETA"))
517 {
518 RemoveConstProperty("MR_NBTHETA");
519 }
520
521 // Adds a new number of thetas
522 AddConstProperty("MR_NBTHETA", (G4double)no_theta);
523
524 //G4cout << "no_theta: " << no_theta << G4endl;
525
526 // Removes an existing number of Energies
527 if(ConstPropertyExists("MR_NBE"))
528 {
529 RemoveConstProperty("MR_NBE");
530 }
531
532 // Adds a new number of Energies
533 AddConstProperty("MR_NBE", (G4double)no_E);
534
535 //G4cout << "no_E: " << no_E << G4endl;
536
537 // Removes an existing minimum theta
538 if(ConstPropertyExists("MR_THETAMIN"))
539 {
540 RemoveConstProperty("MR_THETAMIN");
541 }
542
543 // Adds a new minimum theta
544 AddConstProperty("MR_THETAMIN", theta_min);
545
546 //G4cout << "theta_min: " << theta_min << G4endl;
547
548 // Removes an existing maximum theta
549 if(ConstPropertyExists("MR_THETAMAX"))
550 {
551 RemoveConstProperty("MR_THETAMAX");
552 }
553
554 // Adds a new maximum theta
555 AddConstProperty("MR_THETAMAX", theta_max);
556
557 //G4cout << "theta_max: " << theta_max << G4endl;
558
559 // Removes an existing minimum energy
560 if(ConstPropertyExists("MR_EMIN"))
561 {
562 RemoveConstProperty("MR_EMIN");
563 }
564
565 // Adds a new minimum energy
566 AddConstProperty("MR_EMIN", E_min);
567
568 //G4cout << "Emin: " << E_min << G4endl;
569
570 // Removes an existing maximum energy
571 if(ConstPropertyExists("MR_EMAX"))
572 {
573 RemoveConstProperty("MR_EMAX");
574 }
575
576 // Adds a new maximum energy
577 AddConstProperty("MR_EMAX", E_max);
578
579 //G4cout << "Emax: " << E_max << G4endl;
580
581 // Removes an existing Theta angle number
582 if(ConstPropertyExists("MR_ANGNOTHETA"))
583 {
584 RemoveConstProperty("MR_ANGNOTHETA");
585 }
586
587 // Adds a new Theta angle number
588 AddConstProperty("MR_ANGNOTHETA", (G4double)AngNoTheta);
589
590 //G4cout << "AngNoTheta: " << AngNoTheta << G4endl;
591
592 // Removes an existing Phi angle number
593 if(ConstPropertyExists("MR_ANGNOPHI"))
594 {
595 RemoveConstProperty("MR_ANGNOPHI");
596 }
597
598 // Adds a new Phi angle number
599 AddConstProperty("MR_ANGNOPHI", (G4double)AngNoPhi);
600
601 //G4cout << "AngNoPhi: " << AngNoPhi << G4endl;
602
603 // Removes an existing angular cut
604 if(ConstPropertyExists("MR_ANGCUT"))
605 {
606 RemoveConstProperty("MR_ANGCUT");
607 }
608
609 // Adds a new angle number
610 AddConstProperty("MR_ANGCUT", AngularCut);
611
612 //G4cout << "AngularCut: " << AngularCut/degree << "degree" << G4endl;
613
614 // Starts the lookup table calculation
615
617
618 //G4cout << " *** DONE! ***" << G4endl;
619}
double G4double
Definition: G4Types.hh:83
bool G4bool
Definition: G4Types.hh:86
int G4int
Definition: G4Types.hh:85
#define G4endl
Definition: G4ios.hh:57
G4GLOB_DLL std::ostream G4cout
void AddConstProperty(const G4String &key, G4double propertyValue, G4bool createNewKey=false)
G4bool ConstPropertyExists(const G4String &key) const
G4double GetConstProperty(const G4String &key) const
void RemoveConstProperty(const G4String &key)
G4double GetMRMaxTransProbability(G4double, G4double)
void SetMicroRoughnessParameters(G4double, G4double, G4int, G4int, G4double, G4double, G4double, G4double, G4int, G4int, G4double)
G4double GetMRProbability(G4double, G4double, G4double, G4double, G4double)
G4bool ConditionsValid(G4double E, G4double VFermi, G4double theta_i)
void LoadMicroRoughnessTables(G4double *, G4double *, G4double *, G4double *)
G4bool TransConditionsValid(G4double E, G4double VFermi, G4double theta_i)
void SetMRMaxProbability(G4double, G4double, G4double)
void SetMRMaxTransProbability(G4double, G4double, G4double)
G4double GetMRIntTransProbability(G4double, G4double)
G4double GetMRMaxProbability(G4double, G4double)
G4double GetMRTransProbability(G4double, G4double, G4double, G4double, G4double)
G4double GetMRIntProbability(G4double, G4double)
static G4UCNMicroRoughnessHelper * GetInstance()