KaliVeda
Toolkit for HIC analysis
KVIDZAFromZGridMassCorrector.cpp
1 #include "KVIDZAFromZGridMassCorrector.h"
2 #include "KVGaussFitMassModifier.h"
3 #include "KVMultiGaussIsotopeFit.h"
4 
6 
7 
25 
26 std::vector<KVIDZAFromZGridMassCorrector::mass_correction_t>
28 {
29  // Determine the mass-shifts to apply to each fitted element \f$Z\f$ by comparing the mass distributions with those of the reference fits.
30  //
31  // \param[in] _min_yield minimum yield (expressed as a fraction of the largest yield in the reference fit) above which to consider isotopes in mass distributions
32  //
33  // \note For \f$Z=6\f$ `_min_yield` is fixed at 0.5
34  //
35  // Up to 3 isotope masses will be compared for the 2 fits of each element, depending on the threshold minimum yield parameter.
36  //
37  // If the sequence of masses for the reference & other fit can be related with a single offset (i.e. masses "24,25,26" for one,
38  // masses "23,24,25" for the other implies an offset of \f$\pm 1\f$), then this is taken to be the required mass correction,
39  // unless such a correction would lead to assign a spurious value corresponding to an undetectable resonance etc.
40  //
41  // \note set static member variable KVIDZAFromZGridMassCorrector::fOnlyShowZ to a non-zero value in order to only
42  // consider the given \f$Z\f$. Reset KVIDZAFromZGridMassCorrector::fOnlyShowZ=0 in order to treat all elements.
43  //
44  // \returns a vector containing the mass correction required for each \f$Z\f$
45 
46  refGrid->Initialize();
47  modGrid->Initialize();
48  if(!modGrid->GetFits() || modGrid->GetFits()->IsEmpty())
49  {
50  KVError::Warning(this,"DetermineMassCorrections", "Grid %s has no multi-gaussian mass fits", modGrid->GetName());
51  return {};
52  }
53  if(!refGrid->GetFits() || refGrid->GetFits()->IsEmpty())
54  {
55  KVError::Warning(this,"DetermineMassCorrections", "Grid %s has no multi-gaussian mass fits", refGrid->GetName());
56  return {};
57  }
58  TIter next_fit(refGrid->GetFits());
59  KVMultiGaussIsotopeFit* ref_fit;
60  std::vector<mass_correction_t> corrections;
61  while( (ref_fit = (KVMultiGaussIsotopeFit*)next_fit()) )
62  {
63  auto mod_fit = modGrid->GetMultiGaussFit(ref_fit->GetZ());
64  if(!mod_fit) continue;
65 
66  double min_yield=_min_yield;
67  if(ref_fit->GetZ()==6)
68  {
69  //KVError::Info(this,"DetermineMassCorrections", "Setting threshold to 50% for carbon");
70  min_yield=0.5;
71  }
72 
73  KVNumberList ref_masses,mod_masses;
74  int ngauss = std::min(std::min(ref_fit->GetNGaussians(),mod_fit->GetNGaussians()),3);
75  auto ref_A = ref_fit->GetIsotopesRankedByYield();
76  auto mod_A = mod_fit->GetIsotopesRankedByYield();
77  auto ref_yield = ref_fit->GetRankedYields();
78  auto mod_yield = mod_fit->GetRankedYields();
79  for(int i=0; i<ngauss; ++i)
80  {
81  // only consider the most-produced isotopes (maybe 1, 2 or 3)
82  if(ref_yield[i]>min_yield*ref_yield[0])
83  {
84  ref_masses.Add(ref_A[i]);
85  mod_masses.Add(mod_A[i]);
86  }
87  }
88 
89  if(ref_masses != mod_masses)
90  {
91  if(!fOnlyShowZ || (fOnlyShowZ && ref_fit->GetZ()==fOnlyShowZ))
92  {
93  std::cout << "Z=" << ref_fit->GetZ() << " : " << refGrid->GetName() << " A=" << ref_masses.AsString();
94  std::cout << "\t\t-- " << modGrid->GetName() << " A=" << mod_masses.AsString();
95 
96  auto offset = mod_masses.FindOffset(ref_masses);
97  if(offset) {
98  // check that applying the offset to the complete mass list does not include resonances
99  // or very short-lived isotopes that can never be identified
100  auto alist = mod_fit->GetAlist();
101  KVNucleus test_nuc;
102  bool ok = true;
103  KVNumberList new_masses;
104  for(auto &A : alist)
105  {
106  A+=*offset;
107  new_masses.Add(A);
108  if(test_nuc.IsResonance(ref_fit->GetZ(),A))
109  ok = false;
110  else if(test_nuc.GetLifeTime(ref_fit->GetZ(),A).value_or(1.e+06)<1.e-3)
111  ok = false;
112  else if(not_good[ref_fit->GetZ()].Contains(A))
113  ok = false;
114  }
115  if(ok)
116  {
117  std::cout << "\t\t==> apply DeltaA = " << (*offset>0 ? "+" : "") << *offset;
118  corrections.push_back({ref_fit->GetZ(),*offset});
119  }
120  else
121  {
122  std::cout << "\t\t==> applying DeltaA = " << (*offset>0 ? "+" : "") << *offset << " would lead to masses: " << new_masses.AsString() << " !!!\n";
123  }
124  }
125  else
126  std::cout << " ==> cannot find constant DeltaA to apply...???";
127  std::cout << std::endl;
128  }
129  }
130  }
131  return corrections;
132 }
133 
134 
135 
147 
148 void KVIDZAFromZGridMassCorrector::ApplyCorrections(const std::vector<KVIDZAFromZGridMassCorrector::mass_correction_t>& corrections,
149  TH1* pid_dist,
150  const KVNameValueList& mass_fit_parameters)
151 {
152  // Takes the mass corrections previously determined by DetermineMassCorrections() and applies them to each fit
153  // using KVGaussFitMassModifier
154  //
155  // \param[in] corrections see DetermineMassCorrections()
156  // \param[in] pid_dist a PID distribution corresponding to the grid being used
157  // \param[in] mass_fit_parameters parameters to control fit; by default KVMultiGaussIsotopeFit::mass_fit_parameters
158  //
159  // \note For any KVIDZAGrid, a 1-dimensional PID distribution to be used with multi-gaussian fits
160  // can be generated from a 2D identification map (e.g. \f$\Delta E-E\f$ matrix)
161  // using KVIDZAFromZGrid::LinearizeHistoToPID()
162 
163  for(auto& corr : corrections)
164  {
165  if(pid_dist)
166  {
167  std::cout << "Applying DeltaA=" << corr.second << " to isotopes for Z=" << corr.first << std::endl;
168  KVGaussFitMassModifier gfmm(modGrid, corr.first);
169  gfmm.Modify(corr.second, pid_dist, mass_fit_parameters);
170  }
171  }
172 }
173 
174 
176 
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 offset
Change isotope masses in a multi-gauss fit by fixed offset.
void Modify(int deltaA, TH1 *pid_dist, const KVNameValueList &mass_fit_parameters)
const Char_t * GetName() const override
Definition: KVIDGraph.cpp:1416
Modify masses used in multi-gauss fits of an id-grid to be conform to those of a 'reference' grid.
void ApplyCorrections(const std::vector< KVIDZAFromZGridMassCorrector::mass_correction_t > &, TH1 *pid_dist, const KVNameValueList &mass_fit_parameters)
std::vector< mass_correction_t > DetermineMassCorrections(double min_yield)
void Initialize() override
KVMultiGaussIsotopeFit * GetMultiGaussFit(int z) const
auto GetFits() const
Function for fitting PID mass spectra.
std::vector< double > GetRankedYields() const
std::vector< int > GetIsotopesRankedByYield() const
Handles lists of named parameters with different types, a list of KVNamedParameter objects.
Description of properties and kinematics of atomic nuclei.
Definition: KVNucleus.h:108
std::optional< double > GetLifeTime(std::optional< int > z={}, std::optional< int > a={}) const
Definition: KVNucleus.cpp:1045
Bool_t IsResonance(std::optional< int > z={}, std::optional< int > a={}) const
Definition: KVNucleus.cpp:1961
Strings used to represent a set of ranges of values.
Definition: KVNumberList.h:86
const Char_t * AsString(Int_t maxchars=0) const
void Add(Int_t)
Add value 'n' to the list.
std::optional< int > FindOffset(const KVNumberList &other)
void Warning(UserClass p, const char *location, const char *va_(fmt),...)
Definition: KVError.h:125
ClassImp(TPyArg)