4 #include "KVIDZAFromZGrid.h"
6 #include "KVIDZALine.h"
10 #include "KVMultiGaussIsotopeFit.h"
30 fIgnoreMassID =
false;
55 i.fPIDRange = fPIDRange;
56 i.fPIDRangeZList = fPIDRangeZList;
57 fTables.
Copy(i.fTables);
59 i.fIgnoreMassID = fIgnoreMassID;
82 fIgnoreMassID =
false;
84 check_pidranges_and_massfits();
103 fPIDRangeZList.
Clear();
120 double pidmin, pidmax, pid;
122 else if (
type == 2) {
127 itv->
add(aa, pid, pidmin, pidmax);
131 fPIDRangeZList.
Add(zz);
146 fPIDRangeZList.
Clear();
179 fPIDRangeZList.
Add(ivs->
GetZ());
202 auto z_int = itvs->
GetZ();
203 fPIDRangeZList.
Remove(z_int);
233 fPIDRangeZList.
Clear();
235 for (
int ii = 1; ii < 50; ii++) {
251 int KVIDZAFromZGrid::is_inside(
double pid)
const
268 if (it && it->
is_inside(pid))
return zint + 1;
273 if (it && it->
is_inside(pid))
return zint - 1;
310 for (
auto z : zlist) {
314 fitparams.
Set(massfit);
328 void KVIDZAFromZGrid::check_pidranges_and_massfits()
335 if(fPar.HasParameter(
"MASSFITS"))
341 auto massfits_copy = massfits;
342 massfits.Inter(pidrange);
343 if(massfits != massfits_copy)
345 KVError::Error(
this,
"KVIDZAFromZGrid::check_pidranges_and_massfits",
346 "Grid %s has inconsistent MASSFITS (%s) and PIDRANGE (%s) - correcting...",
347 GetName(), massfits_copy.AsString(), pidrange.AsString());
350 for(
auto z : massfits)
355 "Grid %s : removing fit for Z=%d...",
364 for (
auto z : massfits) {
365 if(pidrange.Contains(z))
370 fitparams.
Set(massfit);
383 auto pipi = pidr.
Next();
385 pidalist.
Add(pipi.Next().Atoi());
387 auto alist_orig = alist;
388 alist.Inter(pidalist);
389 if(alist != alist_orig)
392 "Grid %s has inconsistent masses for Z=%d for MASSFIT (%s) and PIDRANGE (%s)",
407 auto A = fitfunc->
GetA(idr->
PID, P);
452 auto fLinearHisto =
new TH1F(
"fLinearHisto",
"fLinearHisto", zbins, zmin, zmax);
457 auto available_cpu = WITH_MULTICORE_CPU;
460 std::vector<std::thread> jobs;
469 std::cout <<
"Will run " << available_cpu <<
" threads, each for " << xbins_per_cpu <<
" bins in X" << std::endl;
471 int nthreads = available_cpu;
473 std::cout <<
"Histo linearization using " << nthreads <<
" threads..." << std::endl;
475 for (
int job = 0; job < available_cpu; ++job) {
476 auto imin = 1 + job * xbins_per_cpu;
477 auto imax = (job + 1) * xbins_per_cpu;
478 if (job == available_cpu - 1) imax = fHisto->
GetNbinsX();
482 grid_copy->Initialize();
483 grid_copies.
Add(grid_copy);
486 jobs.push_back(std::thread([ =, &nthreads]() {
490 bool no_mass_id_zone_defined = (grid_copy->GetInfos()->
FindObject(
"MassID") ==
nullptr);
492 for (
int i = imin; i <= imax; ++i) {
493 for (
int j = 1; j <= fHisto->
GetNbinsY(); j++) {
495 if (poids == 0)
continue;
502 if (x0 < 4)
continue;
506 Double_t weight = (kmax == 20 ? poids / 20. : 1.);
507 for (
int k = 0; k < kmax; k++) {
510 if (grid_copy->IsIdentifiable(
x,
y)) {
512 grid_copy->KVIDZAGrid::Identify(
x,
y, &idr);
513 if (no_mass_id_zone_defined || idr.
HasFlag(grid_copy->GetName(),
"MassID")) {
515 fLinearHisto->Fill(PID, weight);
522 std::cout <<
"...remaining threads: " << nthreads << std::endl;
525 for (
auto& j : jobs) {
526 if (j.joinable()) j.join();
566 if (!idr->
IDOK)
return;
568 bool have_pid_range_for_Z = fPIDRange && fPIDRangeZList.
Contains(idr->
Z);
570 bool have_mass_fit_for_Z = (mass_fit_for_Z !=
nullptr);
571 bool mass_id_success =
false;
573 if ((have_mass_fit_for_Z || have_pid_range_for_Z)
576 if (have_mass_fit_for_Z)
580 if (mass_id_success) {
605 if (mass_id_success) idr->
SetComment(
"slight ambiguity of A, which could be larger");
606 else idr->
SetComment(
"slight ambiguity of Z, which could be larger");
609 if (mass_id_success) idr->
SetComment(
"slight ambiguity of A, which could be smaller");
610 else idr->
SetComment(
"slight ambiguity of Z, which could be smaller");
613 if (mass_id_success) idr->
SetComment(
"slight ambiguity of A, which could be larger or smaller");
614 else idr->
SetComment(
"slight ambiguity of Z, which could be larger or smaller");
617 if (mass_id_success) idr->
SetComment(
"point is outside of mass identification range");
618 else idr->
SetComment(
"Z identification correct but no mass identification");
621 if (mass_id_success) idr->
SetComment(
"point is in between two isotopes A & A+2 (e.g. 5He, 8Be, 9B)");
622 else idr->
SetComment(
"point is in between two lines of different Z, too far from either to be considered well-identified");
625 idr->
SetComment(
"(x,y) is below first line in grid");
628 idr->
SetComment(
"(x,y) is above last line in grid");
631 idr->
SetComment(
"no identification: (x,y) out of range covered by grid");
651 int zint = is_inside(idr->
PID);
652 if (!zint)
return -1;
653 if (zint != idr->
Z) idr->
Z = zint;
657 if (it) res = it->
eval(idr);
673 if (!itvs->
GetNPID())
continue;
674 fPIDRangeZList.
Add(itvs->
GetZ());
681 if (!itvs->
GetNPID())
continue;
689 KVError::Error(
this,
"ExportToGrid",
"Grid %s has interval set for Z=%d including resonance %s",
699 auto massfits_copy = massfits;
700 massfits.
Inter(fPIDRangeZList);
701 if(massfits != massfits_copy)
703 ::Info(
"KVIDZAFromZGrid::ExportToGrid()",
704 "Grid %s : will correct MASSFITS(%s) to be same as PIDRANGE(%s)",
707 massfits = fPIDRangeZList;
710 for(
auto z : massfits)
714 ::Info(
"KVIDZAFromZGrid::ExportToGrid()",
715 "Grid %s : removing fit for Z=%d for which no PIDRANGE exists (%s)",
731 double pid = idr->
PID;
732 if (pid < 0.5)
return 0.;
742 interval* left_int(
nullptr), *right_int(
nullptr);
747 ares = inter->
GetA();
770 if (!right_int || !left_int) {
778 int dA = right_int->
GetA() - left_int->GetA();
868 std::map<double,int> toto;
872 auto it = std::begin(toto);
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
R__EXTERN TRandom * gRandom
char * Form(const char *fmt,...)
virtual void WriteToAsciiFile(std::ofstream &gridfile)
static void SetAutoAdd(Bool_t yes=kTRUE)
static Bool_t GetAutoAdd()
const Char_t * GetName() const override
const KVNameValueList * GetParameters() const
const KVList * GetIdentifiers() const
Hybrid charge & mass identification grid.
const KVList * GetIntervalSets() const
bool MassIdentificationFromMultiGaussFit(KVMultiGaussIsotopeFit *, KVIdentificationResult *) const
void Initialize() override
KVMultiGaussIsotopeFit * GetMultiGaussFit(int z) const
interval_set * GetIntervalSet(int zint) const
void WriteToAsciiFile(std::ofstream &gridfile) override
void Identify(Double_t x, Double_t y, KVIdentificationResult *) const override
virtual double DeduceAfromPID(KVIdentificationResult *idr) const
void AddIntervalSet(interval_set *)
add an interval set to the grid, updating the corresponding parameters
TH1 * LinearizeHistoToPID(const TH2 *hdata, int nbins=100) const override
void SetOnlyZId(Bool_t=kTRUE) override
void RemoveIntervalSet(int zint)
Remove interval set for given Z from grid.
void ReadFromAsciiFile(std::ifstream &gridfile) override
void Copy(TObject &obj) const override
void ReadFromAsciiFile(std::ifstream &gridfile) override
void Copy(TObject &) const override
Copy this to 'obj'.
void Initialize() override
void Identify(Double_t x, Double_t y, KVIdentificationResult *) const override
Base class for graphical cuts used in particle identification.
virtual Double_t GetPID() const
Full result of one attempted particle identification.
Bool_t IDOK
general quality of identification, =kTRUE if acceptable identification made
void SetComment(const Char_t *c)
Bool_t Aident
= kTRUE if A of particle established
Double_t PID
= "real" Z if Zident==kTRUE and Aident==kFALSE, "real" A if Zident==Aident==kTRUE
Int_t A
A of particle found (if Aident==kTRUE)
Int_t Z
Z of particle found (if Zident==kTRUE)
Int_t IDquality
specific quality code returned by identification procedure
void Clear(Option_t *opt="") override
Reset to initial values.
Bool_t HasFlag(std::string grid_name, TString flag)
Bool_t Zident
=kTRUE if Z of particle established
Extended TList class which owns its objects by default.
Function for fitting PID mass spectra.
std::optional< int > GetA(double PID, double &P) const
double GetInterpolatedA(double PID) const
Handles lists of named parameters with different types, a list of KVNamedParameter objects.
void SetValue(const Char_t *name, value_type value)
void RemoveParameter(const Char_t *name)
const Char_t * GetStringValue(const Char_t *name) const
bool Set(const KVString &)
TString GetTStringValue(const Char_t *name) const
Description of properties and kinematics of atomic nuclei.
const Char_t * GetSymbol(Option_t *opt="") const
Bool_t IsResonance(std::optional< int > z={}, std::optional< int > a={}) const
Strings used to represent a set of ranges of values.
void Inter(const KVNumberList &list)
Bool_t Contains(Int_t val) const
returns kTRUE if the value 'val' is contained in the ranges defined by the number list
void Clear(Option_t *="") override
Empty number list, reset it to initial state.
const Char_t * AsString(Int_t maxchars=0) const
void Remove(Int_t)
Remove value 'n' from the list.
void Add(Int_t)
Add value 'n' to the list.
void Copy(TObject &obj) const override
TObject * First() const override
TObject * Remove(TObject *obj) override
Remove object from list.
void Add(TObject *obj) override
TObject * FindObject(const char *name) const override
void AddLast(TObject *obj) override
Int_t GetSize() const override
void Clear(Option_t *option="") override
TObject * At(Int_t idx) const override
Extension of ROOT TString class which allows backwards compatibility with ROOT v3....
void Begin(TString delim) const
KVString Next(Bool_t strip_whitespace=kFALSE) const
void Add(TObject *obj) override
virtual void SetPoint(Int_t i, Double_t x, Double_t y)
virtual Double_t Eval(Double_t x, TSpline *spline=nullptr, Option_t *option="") const
TObject * FindObject(const char *name) const override
virtual Int_t GetNbinsY() const
virtual Int_t GetNbinsX() const
virtual Double_t GetBinContent(Int_t bin) const
virtual void SetName(const char *name)
virtual void Info(const char *method, const char *msgfmt,...) const
virtual Double_t Uniform(Double_t x1, Double_t x2)
const char * Data() const
Bool_t IsWhitespace() const
TString & Remove(EStripType s, char c)
Bool_t Contains(const char *pat, ECaseCompare cmp=kExact) const
TString & ReplaceAll(const char *s1, const char *s2)
TString GetListOfMasses()
bool is_inside(double pid)
bool is_above(double pid)
void add(int aa, double pid, double pidmin=-1., double pidmax=-1.)
double eval(KVIdentificationResult *idr)
interval_set(int zz, int type)
bool is_right_of(double pid)
bool is_left_of(double pid)
bool is_inside(double pid)
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)