4 #include "KVedaLossMaterial.h"
6 #include "KVIonRangeTable.h"
9 #include "KVedaLossInverseRangeFunction.h"
10 #include "KVedaLoss.h"
15 KVedaLoss* KVedaLossMaterial::fgTable =
nullptr;
23 fEmin(ZMAX_VEDALOSS), fEmax(ZMAX_VEDALOSS), fCoeff(ZMAX_VEDALOSS, std::vector<
Double_t>(14))
26 for (
int i = 0; i < ZMAX_VEDALOSS; i++) {
41 fEmin(ZMAX_VEDALOSS), fEmax(ZMAX_VEDALOSS), fCoeff(ZMAX_VEDALOSS, std::vector<
Double_t>(14))
45 for (
int i = 0; i < ZMAX_VEDALOSS; i++) {
100 if (!fgets(
line, 132, fp)) {
101 KVError::Warning(
this,
"ReadRangeTable",
"Problem reading energy limits in range table file for %s (%s)",
106 if (!strncmp(
line,
"COMPOUND", 8)) {
108 if (fgets(
line, 132, fp)) {}
109 int nel = atoi(
line);
110 for (
int el = 0; el < nel; el++) {
111 if (fgets(
line, 132, fp)) {}
113 sscanf(
line,
"%d %d %d", &z, &
a, &
w);
117 else if (!strncmp(
line,
"MIXTURE", 7)) {
119 if (fgets(
line, 132, fp)) {}
120 int nel = atoi(
line);
121 for (
int el = 0; el < nel; el++) {
122 if (fgets(
line, 132, fp)) {}
125 sscanf(
line,
"%d %d %d %f", &z, &
a, &nat, &
w);
130 if (!fgets(
line, 132, fp)) {
131 KVError::Warning(
this,
"ReadRangeTable",
"Problem reading energy limits in range table file for %s (%s)",
136 while (
line[0] ==
'Z') {
139 if (sscanf(
line,
"Z = %d,%d %f < E/A < %f MeV", &z1,
140 &z2, &e1, &e2) != 4) {
141 KVError::Error(
this,
"ReadRangeTable",
"Problem reading energy limits in range table file for %s (%s)",
146 if (!fgets(
line, 132, fp))
break;
147 for (
int i = z1; i <= z2; i++) {
152 if (
line[0] ==
'\0') {
153 KVError::Error(
this,
"ReadRangeTable",
"Problem with range table file for %s (%s)",
162 fRange =
new TF1(
Form(
"KVedaLossMaterial:%s:Range",
GetType()),
this, &KVedaLossMaterial::RangeFunc,
163 0., 1.e+03, 0,
"KVedaLossMaterial",
"RangeFunc");
164 fRange->SetNpx(my_npx);
166 fStopping =
new TF1(
Form(
"KVedaLossMaterial:%s:StoppingPower",
GetType()),
this, &KVedaLossMaterial::StoppingFunc,
167 0., 1.e+03, 0,
"KVedaLossMaterial",
"StoppingFunc");
168 fStopping->SetNpx(my_npx);
170 my_npx =
gEnv->
GetValue(
"KVedaLoss.EnergyLoss.Npx", 100);
171 fDeltaE =
new TF1(
Form(
"KVedaLossMaterial:%s:EnergyLoss",
GetType()),
this, &KVedaLossMaterial::DeltaEFunc,
172 0., 1.e+03, 0,
"KVedaLossMaterial",
"DeltaEFunc");
173 fDeltaE->SetNpx(my_npx);
175 my_npx =
gEnv->
GetValue(
"KVedaLoss.ResidualEnergy.Npx", 100);
176 fEres =
new TF1(
Form(
"KVedaLossMaterial:%s:ResidualEnergy",
GetType()),
this, &KVedaLossMaterial::EResFunc,
177 0., 1.e+03, 0,
"KVedaLossMaterial",
"EResFunc");
178 fEres->SetNpx(my_npx);
180 for (
int count = 0; count < ZMAX_VEDALOSS; count++) {
182 if (sscanf(
line,
"%lf %lf %lf %lf %lf %lf %lf %lf",
183 &fCoeff[count][0], &fCoeff[count][1],
184 &fCoeff[count][2], &fCoeff[count][3],
185 &fCoeff[count][4], &fCoeff[count][5],
186 &fCoeff[count][6], &fCoeff[count][7])
191 if (!fgets(
line, 132, fp)) {
196 if (sscanf(
line,
"%lf %lf %lf %lf %lf %lf",
197 &fCoeff[count][8], &fCoeff[count][9],
198 &fCoeff[count][10], &fCoeff[count][11],
199 &fCoeff[count][12], &fCoeff[count][13])
209 Double_t emax = fRange->GetMaximumX() - 1;
210 emax /= fCoeff[count][1];
211 Double_t original_emax = fEmax[count];
218 emax = fStopping->GetMinimumX();
219 emax /= fCoeff[count][1];
225 if (fgets(
line, 132, fp)) {}
246 return (E[0] - EResFunc(E,
nullptr));
265 if (R0 < thickness) {
270 fRangeOfLastDE = thickness;
300 par = &fCoeff[Z - 1];
305 for (
int j = 2; j < 7; j++)
310 for (
int jj = 2; jj < 7; jj++)
315 adn = (
y1 - adm *
x1);
316 riso = RF_A / (*par)[1];
317 if (isoAmat > 0.0) riso *= (isoAmat / fAmat);
349 par = &fCoeff[Z - 1];
354 for (
int j = 2; j < 7; j++)
359 for (
int jj = 2; jj < 7; jj++)
364 adn = (
y1 - adm *
x1);
365 riso = RF_A / (*par)[1];
366 if (isoAmat > 0.0) riso *= (isoAmat / fAmat);
387 ran = adm * dleps + adn;
390 ran = (*par)[2] + (*par)[3] * DLEP;
391 ran += (*par)[4] * (DLEP *= dleps);
392 ran += (*par)[5] * (DLEP *= dleps);
393 ran += (*par)[6] * (DLEP *= dleps);
394 ran += (*par)[7] * (DLEP *= dleps);
417 ran = adm * dleps + adn;
422 ran = (*par)[2] + (*par)[3] * DLEP;
424 for (
int i = 4; i < 8; i++) {
425 drande += (i - 2) * (*par)[i] * DLEP;
426 ran += (*par)[i] * (DLEP *= dleps);
485 if (Z == 0)
return 0.0;
505 if (Z == 0)
return 0.0;
526 if (Z == 0)
return 0.0;
546 if (Z == 0)
return 0.0;
566 if (Z == 0)
return 0.0;
593 rangepar = std::vector<Double_t>(fCoeff[Zion - 1].begin() + 2, fCoeff[Zion - 1].
end());
594 Aion = fCoeff[Zion - 1][1];
Option_t Option_t TPoint TPoint const char x2
Option_t Option_t TPoint TPoint const char x1
Option_t Option_t TPoint TPoint const char y2
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char Pixmap_t Pixmap_t PictureAttributes_t attr const char char ret_data h unsigned char height h Atom_t Int_t ULong_t ULong_t unsigned char prop_list Atom_t Atom_t Atom_t Time_t type
Option_t Option_t TPoint TPoint const char y1
char * Form(const char *fmt,...)
virtual const Char_t * GetType() const
static Double_t ProtectedGetX(const TF1 *func, Double_t val, GetX_status &status, std::optional< Double_t > xmin={}, std::optional< Double_t > xmax={})
Material for use in energy loss & range calculations.
void AddCompoundElement(Int_t Z, Int_t A, Int_t Natoms)
void AddMixtureElement(Int_t Z, Int_t A, Int_t Natoms, Double_t Proportion)
Abstract base class for calculation of range & energy loss of charged particles in matter.
Dedicated optimised inversion of range-energy function for KVedaLoss.
Description of material in the KVedaLoss range table.
Float_t GetEminValid(Int_t Z, Int_t A) const override
Double_t GetEResOfIon(Int_t Z, Int_t A, Double_t E, Double_t e, Double_t isoAmat=0.) override
TF1 * GetStoppingFunction(Int_t Z, Int_t A, Double_t isoAmat=0) override
Bool_t ReadRangeTable(FILE *fp)
Double_t GetRangeOfIon(Int_t Z, Int_t A, Double_t E, Double_t isoAmat=0.) override
virtual ~KVedaLossMaterial()
Destructor.
Double_t GetPunchThroughEnergy(Int_t Z, Int_t A, Double_t e, Double_t isoAmat=0.) override
TF1 * GetEResFunction(Double_t e, Int_t Z, Int_t A, Double_t isoAmat=0) override
Float_t GetEmaxValid(Int_t Z, Int_t A) const override
Double_t GetDeltaEOfIon(Int_t Z, Int_t A, Double_t E, Double_t e, Double_t isoAmat=0.) override
void GetParameters(Int_t Zion, Int_t &Aion, std::vector< Double_t > &rangepar)
Double_t GetEIncFromEResOfIon(Int_t Z, Int_t A, Double_t Eres, Double_t e, Double_t isoAmat=0.) override
KVedaLossMaterial()
Default constructor.
TF1 * GetRangeFunction(Int_t Z, Int_t A, Double_t isoAmat=0) override
TF1 * GetDeltaEFunction(Double_t e, Int_t Z, Int_t A, Double_t isoAmat=0) override
C++ implementation of VEDALOSS stopping power calculation.
static Bool_t IsUseNewRangeInversion()
virtual void SetOwner(Bool_t enable=kTRUE)
virtual const char * GetValue(const char *name, const char *dflt) const
virtual void SetRange(Double_t xmin, Double_t xmax)
const char * GetName() const override
void Error(UserClass p, const char *location, const char *va_(fmt),...)
void Warning(UserClass p, const char *location, const char *va_(fmt),...)
Double_t Min(Double_t a, Double_t b)
Double_t Power(Double_t x, Double_t y)
Double_t Max(Double_t a, Double_t b)
#define R0(v, w, x, y, z, i)