MaCh3  2.6.0
Reference Guide
Public Member Functions | Private Member Functions | Private Attributes | List of all members
SampleSummary Class Reference

Class to calculate pvalue produce posterior predictive and many fancy Bayesian stuff [11]. More...

#include <Fitters/SampleSummary.h>

Collaboration diagram for SampleSummary:
[legend]

Public Member Functions

 SampleSummary (const int n_Samples, const std::string &Filename, SampleHandlerInterface *const sample, const int nSteps)
 Constructor. More...
 
 ~SampleSummary ()
 Destructor. More...
 
void AddData (std::vector< TH2Poly * > &DataHist)
 KS: Add data histograms. More...
 
void AddNominal (std::vector< TH2Poly * > &NominalHist, std::vector< TH2Poly * > &W2Nom)
 KS: Add prior histograms. More...
 
void AddThrow (std::vector< TH2Poly * > &MCHist, std::vector< TH2Poly * > &W2Hist, const double LLHPenalty=0.0, const double Weight=1.0, const int DrawNumber=0)
 KS: Add histograms with throws. More...
 
void AddThrowByMode (std::vector< std::vector< TH2Poly * >> &SampleVector_ByMode)
 KS: Add histograms for each mode. More...
 
void Write ()
 KS: Write results into root file. More...
 
void SetLikelihood (const TestStatistic TestStat)
 KS: Set likelihood type. More...
 
void SetNModelParams (const int nPars)
 Set number of model params used for BIC. More...
 

Private Member Functions

void MakePredictive ()
 Finalise the distributions from the thrown samples. More...
 
void PrepareOutput ()
 KS: Prepare output tree and necessary variables. More...
 
void CalcLLH (TH2Poly *const &Data, TH2Poly *const &MC, TH2Poly *const &W2)
 Helper functions to calculate likelihoods using TH2Poly, will modify MC hist title to include LLH. More...
 
void CalcLLH (TH1D *const &Data, TH1D *const &MC, TH1D *const &W2)
 Helper functions to calculate likelihoods using TH1D, will modify MC hist title to include LLH. More...
 
double GetLLH (TH2Poly *const &Data, TH2Poly *const &MC, TH2Poly *const &W2)
 Helper functions to calculate likelihoods using TH2Poly. More...
 
double GetLLH (TH1D *const &Data, TH1D *const &MC, TH1D *const &W2)
 Helper functions to calculate likelihoods using TH1D. More...
 
void PlotBetaParameters ()
 KS: In Barlow Beeston we have Beta Parameters which scale generated MC. More...
 
void StudyKinematicCorrelations ()
 KS: Study how correlated are sample or kinematic bins. More...
 
void MakeCutLLH ()
 Make the cut LLH histogram. More...
 
void MakeCutLLH1D (TH1D *Histogram, double llh_ref=-999)
 
void MakeCutEventRate (TH1D *Histogram, const double DataRate)
 Make the 1D Event Rate Hist. More...
 
void MakeChi2Hists ()
 Make the fluctuated histograms (2D and 1D) for the chi2s Essentially taking the MCMC draws and calculating their LLH to the Posterior predictive distribution And additionally taking the data histogram and calculating the LLH to the predictive distribution Additionally we calculate the chi2 of the draws (fluctuated) of the MC with the prior/posterior predictive and plot it vs the chi2 from the draws of MCMC and the data. More...
 
bool CheckSamples (const int Length)
 Check the length of samples agrees. More...
 
TH1D * ProjectHist (TH2D *Histogram, const bool ProjectX)
 Helper to project TH2D onto axis. More...
 
TH1D * ProjectPoly (TH2Poly *Histogram, const bool ProjectX, const int selection, const bool MakeErrorHist=false)
 Helper to project TH2Poly onto axis. More...
 
void MakeFluctuatedHistogram (TH1D *FluctHist, TH1D *PolyHist)
 Make Poisson fluctuation of TH1D hist. More...
 
void MakeFluctuatedHistogram (TH2Poly *FluctHist, TH2Poly *PolyHist)
 Make Poisson fluctuation of TH2Poly hist. More...
 
void StudyInformationCriterion (M3::kInfCrit Criterion)
 Information Criterion. More...
 
void StudyBIC ()
 Study Bayesian Information Criterion (BIC) [13]. More...
 
void StudyDIC ()
 KS: Get the Deviance Information Criterion (DIC) [33] [35]. More...
 
void StudyWAIC ()
 KS: Get the Watanabe-Akaike information criterion (WAIC) [13] [18]. More...
 

Private Attributes

std::unique_ptr< TRandom3 > rnd
 Random number generator. More...
 
bool first_pass
 KS: Hacky flag to let us know if this is first toy. More...
 
bool StandardFluctuation
 KS: We have two methods for Poissonian fluctuation. More...
 
std::vector< std::vector< TH2Poly * > > MCVector
 Vector of vectors which holds the loaded MC histograms. More...
 
std::vector< std::vector< TH2Poly * > > W2MCVector
 Vector of vectors which holds the loaded W2 histograms. More...
 
std::vector< std::vector< std::vector< TH2Poly * > > > MCVectorByMode
 Vector of vectors which holds the loaded MC histograms for each mode. More...
 
std::vector< double > LLHPenaltyVector
 Vector to hold the penalty term. More...
 
std::vector< double > WeightVector
 Vector holding weight. More...
 
int nSamples
 Number of samples. More...
 
std::vector< std::string > SampleNames
 name for each sample More...
 
std::vector< std::vector< std::unique_ptr< TH1D > > > PosteriorHist
 The posterior predictive for the whole selection: this gets built after adding in the toys. Now an array of Th1ds, 1 for each poly bin, for each sample. More...
 
std::vector< std::vector< std::unique_ptr< TH1D > > > w2Hist
 The posterior predictive for the whole selection: this gets built after adding in the toys. Now an array of Th1ds, 1 for each poly bin, for each sample for W2. More...
 
std::vector< TH2D * > ViolinHists_ProjectX
 Posterior predictive but for X projection but as a violin plot. More...
 
std::vector< TH2D * > ViolinHists_ProjectY
 Posterior predictive but for Y projection but as a violin plot. More...
 
std::vector< TH2Poly * > DataHist
 The data histogram for the selection. More...
 
std::vector< TH1D * > DataHist_ProjectX
 The data histogram for the selection X projection. More...
 
std::vector< TH1D * > DataHist_ProjectY
 The data histogram for the selection Y projection. More...
 
std::vector< TH2Poly * > NominalHist
 The nominal histogram for the selection. More...
 
std::vector< TH2Poly * > W2NomHist
 Pointer to the w2 histograms (for nominal values). More...
 
std::vector< TH2Poly * > W2MeanHist
 Pointer to the w2 histograms (for mean values). More...
 
std::vector< TH2Poly * > W2ModeHist
 Pointer to the w2 histograms (for mode values). More...
 
std::unique_ptr< TH1D > lnLHist
 The histogram containing the lnL for each throw. More...
 
std::unique_ptr< TH1D > lnLHist_drawfluc
 The lnLhist for the draw vs MC fluctuated. More...
 
std::unique_ptr< TH1D > lnLHist_drawflucdraw
 The lnLhist for the draw vs draw fluctuated. More...
 
std::unique_ptr< TH1D > lnLHist_drawdata
 The lnLhist for the draw vs data. More...
 
std::unique_ptr< TH2D > lnLDrawHist
 The 2D lnLhist, showing (draw vs data) and (draw vs fluct), anything above y=x axis is the p-value. More...
 
std::unique_ptr< TH2D > lnLFlucHist
 The 2D lnLHist, showing (draw vs data) and (draw vs draw fluct), anything above y=x axis is the p-value. More...
 
std::unique_ptr< TH2D > lnLDrawHistRate
 The 2D lnLhist, showing (draw vs data) and (draw vs fluct), using rate, anything above y=x axis is the p-value. More...
 
std::unique_ptr< TH2D > lnLFlucHist_ProjectX
 The 2D lnLHist but for ProjectionX histogram (pmu), showing (draw vs data) and (draw vs draw fluct), anything above y=x axis is the p-value. More...
 
std::vector< TH1D * > lnLHist_Sample_DrawData
 The histogram containing the lnL (draw vs data) for each throw for each sample. More...
 
std::vector< TH1D * > lnLHist_Sample_DrawflucDraw
 The histogram containing the lnL (draw vs draw fluct) for each throw for each sample. More...
 
std::vector< TH1D * > lnLHist_Sample_PredflucDraw
 The histogram containing the lnL (draw vs pred fluct) for each throw for each sample. More...
 
std::vector< TH2Poly * > lnLHist_Mean
 The LLH distribution in pmu cosmu for using the mean in each bin. More...
 
std::vector< TH2Poly * > lnLHist_Mode
 The LLH distribution in pmu cosmu for using the mode in each bin. More...
 
std::vector< TH1D * > lnLHist_Mean_ProjectX
 The LLH distribution in pmu using the mean in each bin. More...
 
std::vector< TH2Poly * > MeanHist
 The posterior predictive distribution in pmu cosmu using the mean. More...
 
std::vector< TH2Poly * > MeanHistCorrected
 The posterior predictive distribution in pmu cosmu using the mean after applying Barlow-Beeston Correction. More...
 
std::vector< TH2Poly * > ModeHist
 The posterior predictive distribution in pmu cosmu using the mode. More...
 
std::vector< TH1D * > lnLHist_Mean1D
 Holds the bin-by-bin LLH for the mean posterior predictive vs the data. More...
 
std::vector< TH1D * > lnLHist_Mode1D
 Holds the bin-by-bin LLH for the mode posterior predictive vs the data. More...
 
std::unique_ptr< TH1D > RandomHist
 Holds the history of which entries have been drawn in the MCMC file. More...
 
std::vector< std::vector< std::unique_ptr< TH1D > > > BetaHist
 Distribution of beta parameters in Barlow Beeston formalisms. More...
 
bool DoBetaParam
 Are we making Beta Histograms. More...
 
unsigned int nChainSteps
 Number of throws by user. More...
 
bool isPriorPredictive
 bool whether we have Prior or Posterior Predictive More...
 
bool doShapeOnly
 bool whether to normalise each toy to have shape based p-value and pos pred distribution More...
 
unsigned int nThrows
 Number of throws. More...
 
std::vector< int > maxBins
 Max Number of Bins per each sample. More...
 
double llh_total
 Total LLH for the posterior predictive distribution. More...
 
std::string OutputName
 Output filename. More...
 
TFile * Outputfile
 Output filename. More...
 
std::vector< TDirectory * > Dir
 Directory for each sample. More...
 
TTree * OutputTree
 TTree which we save useful information to. More...
 
std::vector< double > llh_data_draw
 Data vs Draw. More...
 
std::vector< double > llh_drawfluc_draw
 Fluctuated Draw vs Draw. More...
 
std::vector< double > llh_predfluc_draw
 Fluctuated Predictive vs Draw. More...
 
std::vector< double > llh_rate_data_draw
 Data vs Draw using rate only. More...
 
std::vector< double > llh_rate_predfluc_draw
 Fluctuated Predictive vs Draw using rate only. More...
 
std::vector< double > llh_data_drawfluc
 Data vs Fluctuated Draw. More...
 
std::vector< double > llh_data_predfluc
 Data vs Fluctuated Predictive. More...
 
std::vector< double > llh_draw_pred
 Draw vs Predictive. More...
 
std::vector< double > llh_drawfluc_pred
 Fluctuated Draw vs Predictive. More...
 
std::vector< double > llh_predfluc_pred
 Fluctuated Predictive vs Predictive. More...
 
std::vector< double > llh_drawfluc_predfluc
 Fluctuated Draw vs Fluctuated Predictive. More...
 
std::vector< double > llh_datafluc_draw
 Fluctuated Data vs Draw. More...
 
std::vector< double > llh_data_draw_ProjectX
 Projection X (most likely muon momentum) of LLH. More...
 
std::vector< double > llh_drawfluc_draw_ProjectX
 
double llh_penalty
 LLH penalty for each throw. More...
 
double total_llh_data_draw
 Data vs Draw. More...
 
double total_llh_drawfluc_draw
 Fluctuated Draw vs Draw. More...
 
double total_llh_predfluc_draw
 Fluctuated Predictive vs Draw. More...
 
double total_llh_rate_data_draw
 Rate Data vs Draw. More...
 
double total_llh_rate_predfluc_draw
 Fluctuated Predictive vs Draw using Rate. More...
 
double total_llh_data_predfluc
 Data vs Fluctuated Predictive. More...
 
double total_llh_data_drawfluc
 Data vs Fluctuated Draw. More...
 
double total_llh_draw_pred
 Draw vs Predictive. More...
 
double total_llh_drawfluc_pred
 Fluctuated Draw vs Predictive. More...
 
double total_llh_drawfluc_predfluc
 Fluctuated Draw vs Fluctuated Predictive. More...
 
double total_llh_datafluc_draw
 Fluctuated Data vs Draw. More...
 
double total_llh_predfluc_pred
 Fluctuated Predictive vs Predictive. More...
 
double total_llh_data_draw_ProjectX
 Data vs Draw for projection X (most likely muon momentum) More...
 
double total_llh_drawfluc_draw_ProjectX
 Fluctuated Draw vs Draw for projection X (most likely muon momentum) More...
 
bool DoByModePlots
 By mode variables. More...
 
std::vector< std::vector< TH2Poly * > > MeanHist_ByMode
 The posterior predictive distribution in pmu cosmu using the mean. More...
 
TH1D **** PosteriorHist_ByMode
 Histogram which corresponds to each bin in the sample's th2poly. More...
 
SampleHandlerInterfaceSampleHandler
 Pointer to SampleHandler object, mostly used to get sample names, binning etc. More...
 
MaCh3ModesModes
 MaCh3 Modes. More...
 
TestStatistic likelihood
 Type of likelihood for example Poisson, Barlow-Beeston or Ice Cube. More...
 
int nModelParams
 Number of parameters. More...
 
int Debug
 Tells Debug level to save additional histograms. More...
 

Detailed Description

Class to calculate pvalue produce posterior predictive and many fancy Bayesian stuff [11].

For more information, visit the Posterior Predictive page.

Author
Clarence Wret
Kamil Skwarczynski
Warning
This is legacy functionality used only by the ND280 code in T2K. It will be phased out and should not be used for new development.

Definition at line 14 of file SampleSummary.h.

Constructor & Destructor Documentation

◆ SampleSummary()

SampleSummary::SampleSummary ( const int  n_Samples,
const std::string &  Filename,
SampleHandlerInterface *const  sample,
const int  nSteps 
)

Constructor.

Parameters
n_Samplestotal number of samples
Filenamename of output file
samplepointer to sample PDF object
nChainStepsnumber of steps in a chain, 0 indicate prior predictive was used

Definition at line 9 of file SampleSummary.cpp.

9  {
10 // *******************
11  MACH3LOG_DEBUG("Making sample summary class...");
12  #ifdef MULTITHREAD
13  MACH3LOG_DEBUG("With OpenMP and {} threads", omp_get_max_threads());
14  #endif
15 
16  StandardFluctuation = true;
17 
18  if(StandardFluctuation) MACH3LOG_INFO("Using standard method of statistical fluctuation");
19  else MACH3LOG_INFO("Using alternative method of statistical fluctuation, which is much slower");
20 
21  //KS: If true it will print posterior predictive for every beta parameter it is quite useful but make root big number of plots
22  DoBetaParam = true;
23  if(DoBetaParam) MACH3LOG_INFO("I will calculate #beta parameters from Barlow-Beeston formalism");
24 
25  //If true code will normalise each histogram, this way you can calculate shape only error. etc. pvalue will be completely wrong unfortunately
26  doShapeOnly = false;
27 
28  nChainSteps = nSteps;
29  //KS: nChainSteps == 0 means we run PriorPredcitive
30  if(nChainSteps == 0) isPriorPredictive = true;
31  else isPriorPredictive = false;
32 
33  OutputName = Filename;
34  nSamples = n_Samples;
35  SampleHandler = sample;
36 
37  //Get mach3 modes from manager
39 
40  nThrows = 0;
41  first_pass = true;
42  Outputfile = nullptr;
43  OutputTree = nullptr;
44  rnd = std::make_unique<TRandom3>();
45 
46  DataHist.resize(nSamples);
49  NominalHist.resize(nSamples);
50  PosteriorHist.resize(nSamples);
51  W2NomHist.resize(nSamples);
52  w2Hist.resize(nSamples);
53 
56 
57  if(DoBetaParam) BetaHist.resize(nSamples);
58 
59  maxBins.resize(nSamples);
60 
61  lnLHist_Mean.resize(nSamples);
62  lnLHist_Mode.resize(nSamples);
64  MeanHist.resize(nSamples);;
66  ModeHist.resize(nSamples);
67  W2MeanHist.resize(nSamples);
68  W2ModeHist.resize(nSamples);
69  lnLHist_Mean1D.resize(nSamples);
70  lnLHist_Mode1D.resize(nSamples);
74 
75  //KS: When a histogram is created with an axis lower limit greater or equal to its upper limit ROOT will automatically adjust histogram range
76  // https://root.cern.ch/doc/master/classTH1.html#auto-bin
77  lnLHist = std::make_unique<TH1D>("lnLHist_predpredfluc", "lnLHist_predpredfluc", 100, 1, -1);
78  lnLHist->SetDirectory(nullptr);
79  lnLHist->GetXaxis()->SetTitle("-2LLH (Pred Fluc, Pred)");
80  lnLHist->GetYaxis()->SetTitle("Counts");
81 
82  lnLHist_drawdata = std::make_unique<TH1D>("lnLHist_drawdata", "lnLHist_drawdata", 100, 1, -1);
83  lnLHist_drawdata->SetDirectory(nullptr);
84  lnLHist_drawdata->GetXaxis()->SetTitle("-2LLH (Data, Draw)");
85  lnLHist_drawdata->GetYaxis()->SetTitle("Counts");
86 
87  lnLHist_drawfluc = std::make_unique<TH1D>("lnLHist_drawpredfluc", "lnLHist_drawpredfluc", 100, 1, -1);
88  lnLHist_drawfluc->SetDirectory(nullptr);
89  lnLHist_drawfluc->GetXaxis()->SetTitle("-2LLH (Pred Fluc, Draw)");
90  lnLHist_drawfluc->GetYaxis()->SetTitle("Counts");
91 
92  lnLHist_drawflucdraw = std::make_unique<TH1D>("lnLHist_drawflucdraw", "lnLHist_drawflucdraw", 100, 1, -1);
93  lnLHist_drawflucdraw->SetDirectory(nullptr);
94  lnLHist_drawflucdraw->GetXaxis()->SetTitle("-2LLH (Draw Fluc, Draw)");
95  lnLHist_drawflucdraw->GetYaxis()->SetTitle("Counts");
96 
97  lnLDrawHist = std::make_unique<TH2D>("lnLDrawHist", "lnLDrawHist", 50, 1, -1, 50, 1, -1);
98  lnLDrawHist->SetDirectory(nullptr);
99  lnLDrawHist->GetXaxis()->SetTitle("-2LLH_{Pred Fluc, Draw}");
100  lnLDrawHist->GetYaxis()->SetTitle("-2LLH_{Data, Draw}");
101 
102  lnLFlucHist = std::make_unique<TH2D>("lnLFlucHist", "lnLFlucHist", 50, 1, -1, 50, 1, -1);
103  lnLFlucHist->SetDirectory(nullptr);
104  lnLFlucHist->GetXaxis()->SetTitle("-2LLH_{Draw Fluc, Draw}");
105  lnLFlucHist->GetYaxis()->SetTitle("-2LLH_{Data, Draw}");
106 
107  lnLDrawHistRate = std::make_unique<TH2D>("lnLDrawHistRate", "lnLDrawHistRate", 50, 1, -1, 50, 1, -1);
108  lnLDrawHistRate->SetDirectory(nullptr);
109  lnLDrawHistRate->GetXaxis()->SetTitle("-2LLH_{Pred Fluc, Draw}");
110  lnLDrawHistRate->GetYaxis()->SetTitle("-2LLH_{Data, Draw}");
111 
112  //KS: This is silly as it assumes all samples uses same kinematics
113  lnLFlucHist_ProjectX = std::make_unique<TH2D>("lnLFlucHist_ProjectX", "lnLFlucHist_ProjectX", 50, 1, -1, 50, 1, -1);
114  lnLFlucHist_ProjectX->SetDirectory(nullptr);
115  lnLFlucHist_ProjectX->GetXaxis()->SetTitle(("-2LLH_{Draw Fluc, Draw} for " + SampleHandler->GetKinVarName(0, 0)).c_str());
116  lnLFlucHist_ProjectX->GetYaxis()->SetTitle(("-2LLH_{Data, Draw} for " + SampleHandler->GetKinVarName(0, 0)).c_str());
117 
118  // Holds the hist of random number draws, only works for posterior predictive
119  if(!isPriorPredictive)
120  {
121  RandomHist = std::make_unique<TH1D>("RandomHist", "RandomHist", 100, 0, nChainSteps);
122  RandomHist->SetDirectory(nullptr);
123  RandomHist->GetXaxis()->SetTitle("Step");
124  const double binwidth = nChainSteps/RandomHist->GetNbinsX();
125  std::stringstream ss;
126  ss << "Draws/" << binwidth;
127  RandomHist->GetYaxis()->SetTitle(ss.str().c_str());
128  RandomHist->SetLineWidth(2);
129  }
130  else RandomHist = nullptr;
131 
132  for (int i = 0; i < nSamples; ++i)
133  {
134  DataHist[i] = nullptr;
135  DataHist_ProjectX[i] = nullptr;
136  DataHist_ProjectY[i] = nullptr;
137  NominalHist[i] = nullptr;
138 
139  MeanHist[i] = nullptr;
140  if(DoBetaParam) MeanHistCorrected[i] = nullptr;
141  W2MeanHist[i] = nullptr;
142  W2ModeHist[i] = nullptr;
143  lnLHist_Mean[i] = nullptr;
144  lnLHist_Mode[i] = nullptr;
145  lnLHist_Mean_ProjectX[i] = nullptr;
146  lnLHist_Mean1D[i] = nullptr;
147  lnLHist_Mode1D[i] = nullptr;
148  lnLHist_Sample_DrawData[i] = nullptr;
149  lnLHist_Sample_DrawflucDraw[i] = nullptr;
150  lnLHist_Sample_PredflucDraw[i] = nullptr;
151  }//end loop over samples
152 
153  DoByModePlots = false;
154  PosteriorHist_ByMode = nullptr;
155 
156  nModelParams = 0;
157 
158  Debug = 0;
159 }
#define MACH3LOG_DEBUG
Definition: MaCh3Logger.h:34
#define MACH3LOG_INFO
Definition: MaCh3Logger.h:35
MaCh3Modes * GetMaCh3Modes() const
Return pointer to MaCh3 modes.
virtual std::string GetKinVarName(const int iSample, const int Dimension) const =0
Return Kinematic Variable name for specified sample and dimension for example "Reconstructed_Neutrino...
std::vector< TH2Poly * > lnLHist_Mode
The LLH distribution in pmu cosmu for using the mode in each bin.
std::vector< TH2Poly * > lnLHist_Mean
The LLH distribution in pmu cosmu for using the mean in each bin.
std::vector< TH2Poly * > W2MeanHist
Pointer to the w2 histograms (for mean values).
std::unique_ptr< TH1D > RandomHist
Holds the history of which entries have been drawn in the MCMC file.
std::unique_ptr< TRandom3 > rnd
Random number generator.
std::vector< TH1D * > lnLHist_Mode1D
Holds the bin-by-bin LLH for the mode posterior predictive vs the data.
std::string OutputName
Output filename.
std::vector< std::vector< std::unique_ptr< TH1D > > > BetaHist
Distribution of beta parameters in Barlow Beeston formalisms.
int nModelParams
Number of parameters.
std::vector< TH2D * > ViolinHists_ProjectX
Posterior predictive but for X projection but as a violin plot.
bool first_pass
KS: Hacky flag to let us know if this is first toy.
std::vector< TH2Poly * > NominalHist
The nominal histogram for the selection.
std::vector< std::vector< std::unique_ptr< TH1D > > > PosteriorHist
The posterior predictive for the whole selection: this gets built after adding in the toys....
SampleHandlerInterface * SampleHandler
Pointer to SampleHandler object, mostly used to get sample names, binning etc.
std::vector< TH2Poly * > MeanHistCorrected
The posterior predictive distribution in pmu cosmu using the mean after applying Barlow-Beeston Corre...
MaCh3Modes * Modes
MaCh3 Modes.
std::unique_ptr< TH1D > lnLHist
The histogram containing the lnL for each throw.
std::vector< TH1D * > lnLHist_Mean1D
Holds the bin-by-bin LLH for the mean posterior predictive vs the data.
TTree * OutputTree
TTree which we save useful information to.
bool DoByModePlots
By mode variables.
std::vector< TH1D * > lnLHist_Mean_ProjectX
The LLH distribution in pmu using the mean in each bin.
std::vector< TH2Poly * > DataHist
The data histogram for the selection.
int Debug
Tells Debug level to save additional histograms.
std::unique_ptr< TH2D > lnLDrawHist
The 2D lnLhist, showing (draw vs data) and (draw vs fluct), anything above y=x axis is the p-value.
std::vector< TH2D * > ViolinHists_ProjectY
Posterior predictive but for Y projection but as a violin plot.
std::vector< TH2Poly * > ModeHist
The posterior predictive distribution in pmu cosmu using the mode.
std::vector< TH2Poly * > W2NomHist
Pointer to the w2 histograms (for nominal values).
unsigned int nThrows
Number of throws.
std::vector< TH1D * > lnLHist_Sample_DrawData
The histogram containing the lnL (draw vs data) for each throw for each sample.
std::vector< std::vector< std::unique_ptr< TH1D > > > w2Hist
The posterior predictive for the whole selection: this gets built after adding in the toys....
TH1D **** PosteriorHist_ByMode
Histogram which corresponds to each bin in the sample's th2poly.
std::unique_ptr< TH1D > lnLHist_drawflucdraw
The lnLhist for the draw vs draw fluctuated.
TFile * Outputfile
Output filename.
std::unique_ptr< TH2D > lnLDrawHistRate
The 2D lnLhist, showing (draw vs data) and (draw vs fluct), using rate, anything above y=x axis is th...
std::unique_ptr< TH1D > lnLHist_drawdata
The lnLhist for the draw vs data.
int nSamples
Number of samples.
std::vector< TH1D * > DataHist_ProjectX
The data histogram for the selection X projection.
std::vector< TH1D * > DataHist_ProjectY
The data histogram for the selection Y projection.
bool isPriorPredictive
bool whether we have Prior or Posterior Predictive
bool DoBetaParam
Are we making Beta Histograms.
std::vector< TH2Poly * > W2ModeHist
Pointer to the w2 histograms (for mode values).
std::unique_ptr< TH2D > lnLFlucHist
The 2D lnLHist, showing (draw vs data) and (draw vs draw fluct), anything above y=x axis is the p-val...
bool StandardFluctuation
KS: We have two methods for Poissonian fluctuation.
std::unique_ptr< TH2D > lnLFlucHist_ProjectX
The 2D lnLHist but for ProjectionX histogram (pmu), showing (draw vs data) and (draw vs draw fluct),...
std::unique_ptr< TH1D > lnLHist_drawfluc
The lnLhist for the draw vs MC fluctuated.
bool doShapeOnly
bool whether to normalise each toy to have shape based p-value and pos pred distribution
std::vector< TH1D * > lnLHist_Sample_PredflucDraw
The histogram containing the lnL (draw vs pred fluct) for each throw for each sample.
std::vector< TH2Poly * > MeanHist
The posterior predictive distribution in pmu cosmu using the mean.
unsigned int nChainSteps
Number of throws by user.
std::vector< int > maxBins
Max Number of Bins per each sample.
std::vector< TH1D * > lnLHist_Sample_DrawflucDraw
The histogram containing the lnL (draw vs draw fluct) for each throw for each sample.

◆ ~SampleSummary()

SampleSummary::~SampleSummary ( )

Destructor.

Definition at line 163 of file SampleSummary.cpp.

163  {
164 // *******************
165  Outputfile->cd();
166 
167  //ROOT is weird and once you write TFile claim ownership of histograms. Best is to first delete histograms and then close file
168  Outputfile->Close();
169  delete Outputfile;
170 
171  if(DoByModePlots)
172  {
173  for (int i = 0; i < nSamples; ++i)
174  {
175  if(DataHist[i] == nullptr) continue;
176  for (int j = 0; j < Modes->GetNModes()+1; j++)
177  {
178  for (int k = 1; k <= maxBins[i]; ++k)
179  {
180  if(PosteriorHist_ByMode[i][j][k] != nullptr) delete PosteriorHist_ByMode[i][j][k];
181  }
182  delete[] PosteriorHist_ByMode[i][j];
183  if(MeanHist_ByMode[i][j] != nullptr) delete MeanHist_ByMode[i][j];
184  }
185  delete[] PosteriorHist_ByMode[i];
186  }
187  delete[] PosteriorHist_ByMode;
188  }
189 
190  for (int i = 0; i < nSamples; ++i)
191  {
192  if(DataHist[i] == nullptr) continue;
193  if(DataHist[i] != nullptr) delete DataHist[i];
194  if(NominalHist[i] != nullptr) delete NominalHist[i];
195  if(MeanHist[i] != nullptr) delete MeanHist[i];
196  if(ModeHist[i] != nullptr) delete ModeHist[i];
197  if(DoBetaParam && MeanHistCorrected[i] != nullptr) delete MeanHistCorrected[i];
198  if(W2MeanHist[i] != nullptr) delete W2MeanHist[i];
199  if(W2ModeHist[i] != nullptr) delete W2ModeHist[i];
200 
201  if(ViolinHists_ProjectX[i] != nullptr) delete ViolinHists_ProjectX[i];
202  if(ViolinHists_ProjectY[i] != nullptr) delete ViolinHists_ProjectY[i];
203 
204  if(lnLHist_Mean[i] != nullptr) delete lnLHist_Mean[i];
205  if(lnLHist_Mode[i] != nullptr) delete lnLHist_Mode[i];
206  if(lnLHist_Mean_ProjectX[i] != nullptr) delete lnLHist_Mean_ProjectX[i];
207  if(lnLHist_Mean1D[i] != nullptr) delete lnLHist_Mean1D[i];
208  if(lnLHist_Mode1D[i] != nullptr) delete lnLHist_Mode1D[i];
209  if(lnLHist_Sample_DrawData[i] != nullptr) delete lnLHist_Sample_DrawData[i];
210  if(lnLHist_Sample_DrawflucDraw[i] != nullptr) delete lnLHist_Sample_DrawflucDraw[i];
211  if(lnLHist_Sample_PredflucDraw[i] != nullptr) delete lnLHist_Sample_PredflucDraw[i];
212  }
213 }
int GetNModes() const
KS: Get number of modes, keep in mind actual number is +1 greater due to unknown category.
Definition: MaCh3Modes.h:155
std::vector< std::vector< TH2Poly * > > MeanHist_ByMode
The posterior predictive distribution in pmu cosmu using the mean.

Member Function Documentation

◆ AddData()

void SampleSummary::AddData ( std::vector< TH2Poly * > &  DataHist)

KS: Add data histograms.

Parameters
DataHistHistogram with data even rates for each sample

Definition at line 233 of file SampleSummary.cpp.

233  {
234 // *******************
235  const int Length = int(Data.size());
236  // Check length of samples are OK
237  if (!CheckSamples(Length)) throw MaCh3Exception(__FILE__ , __LINE__ );
238  for (int i = 0; i < Length; ++i) {
239  if (Data[i] == nullptr) {
240  DataHist[i] = nullptr;
241  DataHist_ProjectX[i] = nullptr;
242  DataHist_ProjectY[i] = nullptr;
243  maxBins[i] = 0;
244  } else {
245  std::string classname = std::string(DataHist[i]->Class_Name());
246  if(classname == "TH2Poly")
247  {
248  DataHist[i] = static_cast<TH2Poly*>(Data[i]->Clone());
250  DataHist_ProjectX[i] = ProjectPoly(DataHist[i], true, i);
251  DataHist_ProjectY[i] = ProjectPoly(DataHist[i], false, i);
252  maxBins[i] = DataHist[i]->GetNumberOfBins();
253  } else {
254  MACH3LOG_ERROR("Somehow sample {} doesn't use TH2Poly", SampleHandler->GetSampleTitle(i));
255  MACH3LOG_ERROR("Right now I only support TH2Poly but I am ambitious piece of code and surely will have more support in the future");
256  throw MaCh3Exception(__FILE__ , __LINE__ );
257  }
258  }
259  }
260 }
void NormaliseTH2Poly(TH2Poly *Histogram)
Helper to Normalise histograms.
#define MACH3LOG_ERROR
Definition: MaCh3Logger.h:37
Custom exception class used throughout MaCh3.
virtual std::string GetSampleTitle(const int iSample) const =0
Get fancy title for specified samples.
TH1D * ProjectPoly(TH2Poly *Histogram, const bool ProjectX, const int selection, const bool MakeErrorHist=false)
Helper to project TH2Poly onto axis.
bool CheckSamples(const int Length)
Check the length of samples agrees.

◆ AddNominal()

void SampleSummary::AddNominal ( std::vector< TH2Poly * > &  NominalHist,
std::vector< TH2Poly * > &  W2Nom 
)

KS: Add prior histograms.

Definition at line 264 of file SampleSummary.cpp.

264  {
265 // *******************
266  const int Length = int(Nominal.size());
267  if (!CheckSamples(Length)) throw MaCh3Exception(__FILE__ , __LINE__ );
268 
269  //KS: ROOT is super annoying and you cannot use clone with openMP, hence we have another loop below
270  for (int i = 0; i < Length; ++i)
271  {
272  if (Nominal[i] == nullptr) {
273  NominalHist[i] = nullptr;
274  W2NomHist[i] = nullptr;
275  lnLHist_Mean[i] = nullptr;
276  lnLHist_Mode[i] = nullptr;
277  lnLHist_Mean_ProjectX[i] = nullptr;
278  MeanHist[i] = nullptr;
279  if(DoBetaParam) MeanHistCorrected[i] = nullptr;
280  ModeHist[i] = nullptr;
281  W2MeanHist[i] = nullptr;
282  W2ModeHist[i] = nullptr;
283  lnLHist_Sample_DrawData[i] = nullptr;
284  lnLHist_Sample_DrawflucDraw[i] = nullptr;
285  lnLHist_Sample_PredflucDraw[i] = nullptr;
286  // If not nullptr it indicates the selection was turned on, so initialise the privates
287  } else {
288  NominalHist[i] = static_cast<TH2Poly*>(Nominal[i]->Clone());
290  W2NomHist[i] = static_cast<TH2Poly*>(NomW2[i]->Clone());
291 
292  lnLHist_Mean[i] = static_cast<TH2Poly*>(NominalHist[i]->Clone());
293  lnLHist_Mean[i]->SetDirectory(nullptr);
294  lnLHist_Mode[i] = static_cast<TH2Poly*>(NominalHist[i]->Clone());
295  lnLHist_Mode[i]->SetDirectory(nullptr);
296  lnLHist_Mean_ProjectX[i] = static_cast<TH1D*>(DataHist_ProjectX[i]->Clone());
297  MeanHist[i] = static_cast<TH2Poly*>(NominalHist[i]->Clone());
298  if(DoBetaParam) MeanHistCorrected[i] = static_cast<TH2Poly*>(NominalHist[i]->Clone());
299  ModeHist[i] = static_cast<TH2Poly*>(NominalHist[i]->Clone());
300  W2MeanHist[i] = static_cast<TH2Poly*>(NominalHist[i]->Clone());
301  W2ModeHist[i] = static_cast<TH2Poly*>(NominalHist[i]->Clone());
302  }
303  }
304 
305  // Loop over the length of nominal and set the initial distributions up
306  //KS: Don't multithread, mostly due to fact that we initialise histograms
307  for (int i = 0; i < Length; ++i) {
308  // If NULL it indicates the selection was turned off, so initialise all the hists to NULL
309  if (Nominal[i] != nullptr)
310  {
311  std::string name = std::string(NominalHist[i]->GetName());
312  name = name.substr(0, name.find("_nom"));
313 
314  PosteriorHist[i].resize(maxBins[i]+1);
315  w2Hist[i].resize(maxBins[i]+1);
316 
317  if(DoBetaParam) BetaHist[i].resize(maxBins[i]+1);
318 
319  for (int j = 0; j <= maxBins[i]; ++j)
320  {
321  PosteriorHist[i][j] = nullptr;
322  }
323  lnLHist_Mean[i]->SetNameTitle((name+"_MeanlnL").c_str(), (name+"_MeanlnL").c_str());
324  lnLHist_Mean[i]->Reset("");
325  lnLHist_Mean[i]->GetZaxis()->SetTitle("-2lnL_{sample} #times sign(MC-data)");
326 
327  lnLHist_Mode[i]->SetNameTitle((name+"_ModelnL").c_str(), (name+"_ModelnL").c_str());
328  lnLHist_Mode[i]->Reset("");
329  lnLHist_Mode[i]->GetZaxis()->SetTitle("-2lnL_{sample} #times sign(MC-data)");
330 
331  lnLHist_Mean_ProjectX[i]->SetNameTitle((name+"_MeanlnL_ProjectX").c_str(), (name+"_MeanlnL_ProjectX").c_str());
332  lnLHist_Mean_ProjectX[i]->Reset("");
333  lnLHist_Mean_ProjectX[i]->GetYaxis()->SetTitle("-2lnL_{sample} #times sign(MC-data)");
334 
335  MeanHist[i]->SetNameTitle((name+"_mean").c_str(), (name+"_mean").c_str());
336  MeanHist[i]->Reset("");
337  MeanHist[i]->GetZaxis()->SetTitle("Mean");
338 
339  if(DoBetaParam)
340  {
341  MeanHistCorrected[i]->SetNameTitle((name+"_mean_corrected").c_str(), (name+"_mean_corrected").c_str());
342  MeanHistCorrected[i]->Reset("");
343  MeanHistCorrected[i]->GetZaxis()->SetTitle("Mean");
344  }
347 
348  //KS: Y axis is number of events to get estimate of maximal number we use integral
349  const int MaxBinning = doShapeOnly ? 1 : int(NoOverflowIntegral(NominalHist[i])/4);
350  ViolinHists_ProjectX[i] = new TH2D((name+"_Violin_ProjectX").c_str(), (name+"_Violin_ProjectX").c_str(), int(xbins.size()-1), &xbins[0] , 400, 0, MaxBinning);
351  ViolinHists_ProjectX[i]->GetYaxis()->SetTitle("Events");
352  ViolinHists_ProjectX[i]->GetXaxis()->SetTitle(std::string(NominalHist[i]->GetXaxis()->GetTitle()).c_str() );
353  ViolinHists_ProjectX[i]->SetDirectory(nullptr);
354 
355  ViolinHists_ProjectY[i] = new TH2D((name+"_Violin_ProjectY").c_str(), (name+"_Violin_ProjectY").c_str(), int(ybins.size()-1), &ybins[0] , 400, 0, MaxBinning);
356  ViolinHists_ProjectY[i]->GetYaxis()->SetTitle("Events");
357  ViolinHists_ProjectY[i]->GetXaxis()->SetTitle(std::string(NominalHist[i]->GetYaxis()->GetTitle()).c_str());
358  ViolinHists_ProjectY[i]->SetDirectory(nullptr);
359 
360  ModeHist[i]->SetNameTitle((name+"_mode").c_str(), (name+"_mode").c_str());
361  ModeHist[i]->Reset("");
362  ModeHist[i]->GetZaxis()->SetTitle("Mode");
363 
364  W2MeanHist[i]->SetNameTitle((name+"_w2mean").c_str(), (name+"_w2mean").c_str());
365  W2MeanHist[i]->Reset("");
366  W2MeanHist[i]->GetZaxis()->SetTitle("W2Mean");
367 
368  W2ModeHist[i]->SetNameTitle((name+"_w2mode").c_str(), (name+"_w2mode").c_str());
369  W2ModeHist[i]->Reset("");
370  W2ModeHist[i]->GetZaxis()->SetTitle("W2Mode");
371 
372  // Declare the lnL histograms
373  lnLHist_Mean1D[i] = new TH1D((name+"_MeanlnL1D").c_str(),(name+"_MeanlnL1D").c_str(), 50, 1, -1);
374  lnLHist_Mean1D[i]->GetXaxis()->SetTitle("-2LLH (Data, Pred)");
375  lnLHist_Mean1D[i]->GetYaxis()->SetTitle("Counts");
376 
377  lnLHist_Mode1D[i] = new TH1D((name+"_ModelnL1D").c_str(),(name+"_ModelnL1D").c_str(), 50, 1, -1);
378  lnLHist_Mode1D[i]->GetXaxis()->SetTitle("-2LLH (Data, Pred)");
379  lnLHist_Mode1D[i]->GetYaxis()->SetTitle("Counts");
380 
381  lnLHist_Sample_DrawData[i] = new TH1D((name+"_lnLdrawdata").c_str(),(name+"_lnL").c_str(), 100, 1, -1);
382  lnLHist_Sample_DrawData[i]->GetXaxis()->SetTitle("-2LLH (Data, Draw)");
383  lnLHist_Sample_DrawData[i]->GetYaxis()->SetTitle("Counts");
384 
385  lnLHist_Sample_DrawflucDraw[i] = new TH1D((name+"_lnLdrawfluc").c_str(),(name+"_lnL").c_str(), 100, 1, -1);
386  lnLHist_Sample_DrawflucDraw[i]->GetXaxis()->SetTitle("-2LLH (Draw Fluc, Draw)");
387  lnLHist_Sample_DrawflucDraw[i]->GetYaxis()->SetTitle("Counts");
388 
389  lnLHist_Sample_PredflucDraw[i] = new TH1D((name+"_lnLpredfluc").c_str(),(name+"_lnL").c_str(), 100, 1, -1);
390  lnLHist_Sample_PredflucDraw[i]->GetXaxis()->SetTitle("-2LLH (Pred Fluc, Draw)");
391  lnLHist_Sample_PredflucDraw[i]->GetYaxis()->SetTitle("Counts");
392  }
393  }
394  //KS: Separate loop for thread safe reasons
395  for (int i = 0; i < Length; ++i)
396  {
397  //KS: We copy histograms so delete original
398  delete Nominal[i];
399  delete NomW2[i];
400  }
401 }
double NoOverflowIntegral(TH2Poly *poly)
WP: Helper function for calculating binned Integral of TH2Poly i.e not including overflow.
virtual std::vector< double > ReturnKinematicParameterBinning(const int Sample, const std::string &KinematicParameter) const =0
Return the binning used to draw a kinematic parameter.
int int_t
Definition: Core.h:38

◆ AddThrow()

void SampleSummary::AddThrow ( std::vector< TH2Poly * > &  MCHist,
std::vector< TH2Poly * > &  W2Hist,
const double  LLHPenalty = 0.0,
const double  Weight = 1.0,
const int  DrawNumber = 0 
)

KS: Add histograms with throws.

Definition at line 406 of file SampleSummary.cpp.

406  {
407 // *******************
408  nThrows++;
409  //KS: Only make sense for PosteriorPredictive
410  if( !isPriorPredictive )RandomHist->Fill(DrawNumber);
411 
412  const int size = int(SampleVector.size());
413  if (!CheckSamples(size)) throw MaCh3Exception(__FILE__ , __LINE__ );
414 
415  // Push back the throw
416  MCVector.push_back(SampleVector);
417  LLHPenaltyVector.push_back(LLHPenalty);
418  WeightVector.push_back(Weight);
419  W2MCVector.push_back(W2Vec);
420 
421  // Initialise the posterior hist
422  if (first_pass)
423  {
424  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
425  {
426  const int nXBins = 500;
427  //Initialise TH1D which corresponds to each bin in the sample's th2poly
428  std::string name = std::string(SampleVector[SampleNum]->GetName());
429  for (int i = 1; i <= maxBins[SampleNum]; ++i)
430  {
431  //Get PolyBin
432  TH2PolyBin* bin = static_cast<TH2PolyBin*>(SampleVector[SampleNum]->GetBins()->At(i-1));
433 
434  // Just make a little fancy name
435  std::stringstream ss2;
436  ss2 << name << "_";
437  ss2 << "p_{#mu} (" << bin->GetXMin() << "-" << bin->GetXMax() << ")";
438  ss2 << " cos#theta_{#mu} (" << bin->GetYMin() << "-" << bin->GetYMax() << ")";
439 
440  PosteriorHist[SampleNum][i] = std::make_unique<TH1D>(ss2.str().c_str(), ss2.str().c_str(),nXBins, 1, -1);
441  PosteriorHist[SampleNum][i]->SetDirectory(nullptr);
442  w2Hist[SampleNum][i] = std::make_unique<TH1D>(("w2_"+ss2.str()).c_str(), ("w2_"+ss2.str()).c_str(),nXBins, 1, -1);
443  w2Hist[SampleNum][i]->SetDirectory(nullptr);
444  if(DoBetaParam)
445  {
446  std::string betaName = "#beta_param_";
447  BetaHist[SampleNum][i] = std::make_unique<TH1D>((betaName + ss2.str()).c_str(), (betaName + ss2.str()).c_str(), 70, 1, -1);
448  BetaHist[SampleNum][i]->SetDirectory(nullptr);
449  BetaHist[SampleNum][i]->GetXaxis()->SetTitle("#beta parameter value");
450  BetaHist[SampleNum][i]->GetYaxis()->SetTitle("Counts");
451  }
452  } //end loop over bins
453  }//end loop over samples
454  }
455  first_pass = false;
456 
457  // Loop over the samples
458  #ifdef MULTITHREAD
459  #pragma omp parallel for
460  #endif
461  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
462  {
463  if (SampleVector[SampleNum] == nullptr) continue;
464  if(doShapeOnly) NormaliseTH2Poly(SampleVector[SampleNum]);
465  // Loop over the distribution and fill the prior/posterior predictive
466  for (int i = 1; i <= maxBins[SampleNum]; ++i) {
467  const double Content = SampleVector[SampleNum]->GetBinContent(i);
468  PosteriorHist[SampleNum][i]->Fill(Content, Weight);
469  const double w2 = W2Vec[SampleNum]->GetBinContent(i);
470  w2Hist[SampleNum][i]->Fill(w2, Weight);
471  if(DoBetaParam)
472  {
473  const double data = DataHist[SampleNum]->GetBinContent(i);
474  const double BetaParam = GetBetaParameter(data, Content, w2, likelihood);
475  BetaHist[SampleNum][i]->Fill(BetaParam, Weight);
476  }
477  } // end bin loop
478  } // end samples loop
479 } // end AddThrow
double GetBetaParameter(const double data, const double mc, const double w2, const TestStatistic TestStat)
KS: Calculate Beta parameter which will be different based on specified test statistic.
std::vector< double > LLHPenaltyVector
Vector to hold the penalty term.
std::vector< std::vector< TH2Poly * > > MCVector
Vector of vectors which holds the loaded MC histograms.
std::vector< std::vector< TH2Poly * > > W2MCVector
Vector of vectors which holds the loaded W2 histograms.
TestStatistic likelihood
Type of likelihood for example Poisson, Barlow-Beeston or Ice Cube.
std::vector< double > WeightVector
Vector holding weight.

◆ AddThrowByMode()

void SampleSummary::AddThrowByMode ( std::vector< std::vector< TH2Poly * >> &  SampleVector_ByMode)

KS: Add histograms for each mode.

Definition at line 484 of file SampleSummary.cpp.

484  {
485 // *******************
486  MCVectorByMode.push_back(SampleVector_ByMode);
487 
488  //KS: This means this is first time
489  if(!DoByModePlots)
490  {
491  MACH3LOG_INFO("Turning reaction breadkwon mode, brum brum");
492  PosteriorHist_ByMode = new TH1D***[nSamples];
493  MeanHist_ByMode.resize(nSamples);
494  for (int SampleNum = 0; SampleNum < nSamples; SampleNum++)
495  {
496  if (DataHist[SampleNum] == nullptr) continue;
497 
498  PosteriorHist_ByMode[SampleNum] = new TH1D**[Modes->GetNModes()+1];
499  MeanHist_ByMode[SampleNum].resize(Modes->GetNModes()+1);
500  for (int j = 0; j < Modes->GetNModes()+1; j++)
501  {
502  PosteriorHist_ByMode[SampleNum][j] = new TH1D*[maxBins[SampleNum]+1];
503  constexpr int nXBins = 500;
504 
505  std::string name = std::string(NominalHist[SampleNum]->GetName());
506  name = name.substr(0, name.find("_nom"));
507  name = name + "_"+Modes->GetMaCh3ModeName(j);
508 
509  for (int i = 1; i <= maxBins[SampleNum]; i++)
510  {
511  //Get PolyBin
512  TH2PolyBin* bin = static_cast<TH2PolyBin*>(NominalHist[SampleNum]->GetBins()->At(i-1));
513 
514  // Just make a little fancy name
515  std::stringstream ss2;
516  ss2 << name << "_";
517  ss2 << "p_{#mu} (" << bin->GetXMin() << "-" << bin->GetXMax() << ")";
518  ss2 << " cos#theta_{#mu} (" << bin->GetYMin() << "-" << bin->GetYMax() << ")";
519 
520  //Initialise TH1D which corresponds to each bin in the sample's th2poly
521  PosteriorHist_ByMode[SampleNum][j][i] = new TH1D((name+ss2.str()).c_str(),(name+ss2.str()).c_str(),nXBins, 1, -1);
522  }
523  MeanHist_ByMode[SampleNum][j] = static_cast<TH2Poly*>(NominalHist[SampleNum]->Clone());
524  MeanHist_ByMode[SampleNum][j]->SetNameTitle((name+"_mean").c_str(), (name+"_mean").c_str());
525  MeanHist_ByMode[SampleNum][j]->Reset("");
526  MeanHist_ByMode[SampleNum][j]->GetZaxis()->SetTitle("Mean");
527  }
528  }
529  }
530  DoByModePlots = true;
531  // Loop over the sameples
532  #ifdef MULTITHREAD
533  #pragma omp parallel for
534  #endif
535  for (int SampleNum = 0; SampleNum < nSamples; SampleNum++)
536  {
537  if (DataHist[SampleNum] == nullptr) continue;
538 
539  for (int j = 0; j < Modes->GetNModes()+1; j++)
540  {
541  if(doShapeOnly) NormaliseTH2Poly(SampleVector_ByMode[SampleNum][j]);
542  // Loop over the distribution and fill the prior/posterior predictive
543  for (int i = 1; i <= maxBins[SampleNum]; ++i)
544  {
545  const double Content = SampleVector_ByMode[SampleNum][j]->GetBinContent(i);
546  const int Entries = int(PosteriorHist_ByMode[SampleNum][j][i]->GetEntries());
547  PosteriorHist_ByMode[SampleNum][j][i]->Fill(Content, WeightVector[Entries]);
548  }
549  }
550  }
551 } // end AddThrowByMode
std::string GetMaCh3ModeName(const int Index) const
KS: Get normal name of mode, if mode not known you will get UNKNOWN_BAD.
Definition: MaCh3Modes.cpp:156
std::vector< std::vector< std::vector< TH2Poly * > > > MCVectorByMode
Vector of vectors which holds the loaded MC histograms for each mode.

◆ CalcLLH() [1/2]

void SampleSummary::CalcLLH ( TH1D *const &  Data,
TH1D *const &  MC,
TH1D *const &  W2 
)
inlineprivate

Helper functions to calculate likelihoods using TH1D, will modify MC hist title to include LLH.

Parameters
Datahistogram with data distribution for a single sample
MChistogram with MC distribution for a single sample
W2histogram with W2 distribution for a single sample

Definition at line 1556 of file SampleSummary.cpp.

1556  {
1557 // ****************
1558  const double llh = GetLLH(DatHist, MCHist, W2Hist);
1559  std::stringstream ss;
1560  ss << "_2LLH=" << llh;
1561  MCHist->SetTitle((std::string(MCHist->GetTitle())+ss.str()).c_str());
1562  MACH3LOG_INFO("{:<55} {:<10.2f} {:<10.2f} {:<10.2f}", MCHist->GetName(), DatHist->Integral(), MCHist->Integral(), llh);
1563 }
double GetLLH(TH2Poly *const &Data, TH2Poly *const &MC, TH2Poly *const &W2)
Helper functions to calculate likelihoods using TH2Poly.

◆ CalcLLH() [2/2]

void SampleSummary::CalcLLH ( TH2Poly *const &  Data,
TH2Poly *const &  MC,
TH2Poly *const &  W2 
)
inlineprivate

Helper functions to calculate likelihoods using TH2Poly, will modify MC hist title to include LLH.

Parameters
Datahistogram with data distribution for a single sample
MChistogram with MC distribution for a single sample
W2histogram with W2 distribution for a single sample

Definition at line 1567 of file SampleSummary.cpp.

1567  {
1568 // ****************
1569  const double llh = GetLLH(DatHist, MCHist, W2Hist);
1570  std::stringstream ss;
1571  ss << "_2LLH=" << llh;
1572  MCHist->SetTitle((std::string(MCHist->GetTitle())+ss.str()).c_str());
1573  MACH3LOG_INFO("{:<55} {:<10.2f} {:<10.2f} {:<10.2f}", MCHist->GetName(), NoOverflowIntegral(DatHist), NoOverflowIntegral(MCHist), llh);
1574 }

◆ CheckSamples()

bool SampleSummary::CheckSamples ( const int  Length)
inlineprivate

Check the length of samples agrees.

Definition at line 217 of file SampleSummary.cpp.

217  {
218 // *******************
219  bool ok = (nSamples == Length);
220  if (!ok) {
221  MACH3LOG_ERROR("Size of SampleVector input != number of defined samples");
222  MACH3LOG_ERROR("Size of SampleVector: {}", Length);
223  MACH3LOG_ERROR("Size of defined samples: {}", nSamples);
224  MACH3LOG_ERROR("Something has gone wrong with making the Samples");
225  throw MaCh3Exception(__FILE__ , __LINE__ );
226  }
227  return ok;
228 }

◆ GetLLH() [1/2]

double SampleSummary::GetLLH ( TH1D *const &  Data,
TH1D *const &  MC,
TH1D *const &  W2 
)
inlineprivate

Helper functions to calculate likelihoods using TH1D.

Parameters
Datahistogram with data distribution for a single sample
MChistogram with MC distribution for a single sample
W2histogram with W2 distribution for a single sample

Definition at line 1592 of file SampleSummary.cpp.

1592  {
1593 // ****************
1594  double llh = 0.0;
1595  for (int i = 1; i <= DatHist->GetXaxis()->GetNbins(); ++i)
1596  {
1597  const double data = DatHist->GetBinContent(i);
1598  const double mc = MCHist->GetBinContent(i);
1599  const double w2 = W2Hist->GetBinContent(i);
1600  llh += SampleHandler->GetTestStatLLH(data, mc, w2);
1601  }
1602  //KS: do times 2 because banff reports chi2
1603  return 2*llh;
1604 }
double GetTestStatLLH(const double data, const double mc, const double w2) const
Calculate test statistic for a single bin. Calculation depends on setting of fTestStatistic....

◆ GetLLH() [2/2]

double SampleSummary::GetLLH ( TH2Poly *const &  Data,
TH2Poly *const &  MC,
TH2Poly *const &  W2 
)
inlineprivate

Helper functions to calculate likelihoods using TH2Poly.

Parameters
Datahistogram with data distribution for a single sample
MChistogram with MC distribution for a single sample
W2histogram with W2 distribution for a single sample

Definition at line 1577 of file SampleSummary.cpp.

1577  {
1578 // ****************
1579  double llh = 0.0;
1580  for (int i = 1; i < DatHist->GetNumberOfBins()+1; ++i)
1581  {
1582  const double data = DatHist->GetBinContent(i);
1583  const double mc = MCHist->GetBinContent(i);
1584  const double w2 = W2Hist->GetBinContent(i);
1585  llh += SampleHandler->GetTestStatLLH(data, mc, w2);
1586  }
1587  //KS: do times 2 because banff reports chi2
1588  return 2*llh;
1589 }

◆ MakeChi2Hists()

void SampleSummary::MakeChi2Hists ( )
inlineprivate

Make the fluctuated histograms (2D and 1D) for the chi2s Essentially taking the MCMC draws and calculating their LLH to the Posterior predictive distribution And additionally taking the data histogram and calculating the LLH to the predictive distribution Additionally we calculate the chi2 of the draws (fluctuated) of the MC with the prior/posterior predictive and plot it vs the chi2 from the draws of MCMC and the data.

Definition at line 1129 of file SampleSummary.cpp.

1129  {
1130 // *******************
1131  MACH3LOG_INFO("Making the chi2 histograms...");
1132  // Have this to signify if we're doing the first pass
1133  first_pass = true;
1134 
1135  double AveragePenalty = 0;
1136 
1137  // Vectors to hold exact LLH
1138  std::vector<double> LLH_PredFluc_V(nThrows);
1139  std::vector<double> LLH_DataDraw_V(nThrows);
1140  std::vector<double> LLH_DrawFlucDraw_V(nThrows);
1141 
1142  // Loop over the draws
1143  // Should look into multi-threading this. Would require temporary THxx structures from arrays
1144  //KS: Update above would be ideal but currently we loop over samples (see loop below) which isn't as efficient as loop over throws but much much easier to implement
1145  for (unsigned int i = 0; i < nThrows; ++i)
1146  {
1147  if (i % (nThrows/10) == 0) {
1149  }
1150 
1151  // Set the total LLH to zero to initialise
1152  double total_llh_data_draw_temp = 0.0;
1153  double total_llh_drawfluc_draw_temp = 0.0;
1154  double total_llh_predfluc_draw_temp = 0.0;
1155 
1156  double total_llh_rate_data_draw_temp = 0.0;
1157  double total_llh_rate_predfluc_draw_temp = 0.0;
1158 
1159  double total_llh_data_drawfluc_temp = 0.0;
1160  double total_llh_data_predfluc_temp = 0.0;
1161  double total_llh_draw_pred_temp = 0.0;
1162  double total_llh_drawfluc_pred_temp = 0.0;
1163  double total_llh_drawfluc_predfluc_temp = 0.0;
1164  double total_llh_predfluc_pred_temp = 0.0;
1165  double total_llh_datafluc_draw_temp = 0.0;
1166 
1167  double total_llh_data_draw_ProjectX_temp = 0.0;
1168  double total_llh_drawfluc_draw_ProjectX_temp = 0.0;
1169 
1170  // Save the double that gets written to file
1172  AveragePenalty += llh_penalty;
1173 
1174  // Make the Poisson fluctuated hist
1175  std::vector<TH2Poly*> FluctHist(nSamples);
1176  // Also Poisson fluctuate the drawn MCMC hist
1177  std::vector<TH2Poly*> FluctDrawHist(nSamples);
1178  // Finally Poisson fluctuate the data histogram
1179  std::vector<TH2Poly*> DataFlucHist(nSamples);
1180 
1181  // Finally Poisson fluctuate the data histogram
1182  std::vector<TH1D*> FluctDrawHistProjectX(nSamples);
1183  std::vector<TH1D*> DrawHistProjectX(nSamples);
1184  std::vector<TH1D*> DrawHistProjectY(nSamples);
1185  std::vector<TH1D*> DrawW2HistProjectX(nSamples);
1186 
1187  //KS: We have to clone histograms here to avoid cloning in MP loop, we have to make sure binning matches, content doesn't have to
1188  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
1189  {
1190  FluctHist[SampleNum] = static_cast<TH2Poly*>(MeanHist[SampleNum]->Clone());
1191  FluctDrawHist[SampleNum] = static_cast<TH2Poly*>(MeanHist[SampleNum]->Clone());
1192  DataFlucHist[SampleNum] = static_cast<TH2Poly*>(MeanHist[SampleNum]->Clone());
1193 
1194  FluctDrawHistProjectX[SampleNum] = static_cast<TH1D*>(DataHist_ProjectX[SampleNum]->Clone());
1195 
1196  // Get the ith draw for the jth sample
1197  TH2Poly *DrawHist = MCVector[i][SampleNum];
1198  TH2Poly *DrawW2Hist = W2MCVector[i][SampleNum];
1199 
1200  //ProjectPoly calls new TH1D under the hood, never define new ROOT object under MP...
1201  DrawHistProjectX[SampleNum] = ProjectPoly(DrawHist, true, SampleNum);
1202  DrawW2HistProjectX[SampleNum] = ProjectPoly(DrawW2Hist, true, SampleNum);
1203  DrawHistProjectY[SampleNum] = ProjectPoly(DrawHist, false, SampleNum);
1204  }
1205  #ifdef MULTITHREAD
1206  //KS: might be most obscure OMP reduction I have ever made...
1207  #pragma omp parallel for reduction(+:total_llh_data_draw_temp, total_llh_drawfluc_draw_temp, total_llh_predfluc_draw_temp, total_llh_rate_data_draw_temp, total_llh_rate_predfluc_draw_temp, total_llh_data_drawfluc_temp, total_llh_data_predfluc_temp, total_llh_draw_pred_temp, total_llh_drawfluc_pred_temp, total_llh_drawfluc_predfluc_temp, total_llh_predfluc_pred_temp, total_llh_datafluc_draw_temp, total_llh_data_draw_ProjectX_temp, total_llh_drawfluc_draw_ProjectX_temp)
1208  #endif
1209  // Loop over the samples
1210  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
1211  {
1212  // Get the ith draw for the jth sample
1213  TH2Poly *DrawHist = MCVector[i][SampleNum];
1214  TH2Poly *DrawW2Hist = W2MCVector[i][SampleNum];
1215  // Skip empty samples
1216  if (DrawHist == nullptr) continue;
1217 
1218  // Add LLH penalties from the systematics to the LLH that use the drawn histogram
1219  // Data vs Draw
1220  llh_data_draw[SampleNum] = llh_penalty;
1221  // Fluctuated Draw vs Draw
1222  llh_drawfluc_draw[SampleNum] = llh_penalty;
1223  // Fluctuated Predicitve vs Draw
1224  llh_predfluc_draw[SampleNum] = llh_penalty;
1225 
1226  // Data vs Draw using rate
1227  llh_rate_data_draw[SampleNum] = llh_penalty;
1228  // Fluctuated Predicitve vs Draw using rate
1229  llh_rate_predfluc_draw[SampleNum] = llh_penalty;
1230 
1231  // Data vs Fluctuated Draw
1232  llh_data_drawfluc[SampleNum] = llh_penalty;
1233  // Draw vs Predictive
1234  llh_draw_pred[SampleNum] = llh_penalty;
1235  // Fluctuated Draw vs Predictive
1236  llh_drawfluc_pred[SampleNum] = llh_penalty;
1237  // Fluctuated Draw vs Fluctuated Predictive
1238  llh_drawfluc_predfluc[SampleNum] = llh_penalty;
1239  // Fluctuated Data vs Draw
1240  llh_datafluc_draw[SampleNum] = llh_penalty;
1241 
1242  //Some LLH for 1D projections
1243  llh_data_draw_ProjectX[SampleNum] = llh_penalty;
1245 
1246  //Other get 0 penalty term
1247  // Fluctuated Predictive vs Predictive
1248  llh_predfluc_pred[SampleNum] = 0.0;
1249  // Data vs Fluctuated Predictive
1250  llh_data_predfluc[SampleNum] = 0.0;
1251 
1252  // Make the Poisson fluctuated hist
1253  MakeFluctuatedHistogram(FluctHist[SampleNum], MeanHist[SampleNum]);
1254  // Also Poisson fluctuate the drawn MCMC hist
1255  MakeFluctuatedHistogram(FluctDrawHist[SampleNum], DrawHist);
1256  // Finally Poisson fluctuate the data histogram
1257  MakeFluctuatedHistogram(DataFlucHist[SampleNum], DataHist[SampleNum]);
1258 
1259  // Likelihood between the drawn histogram and the data
1260  const double DataDrawLLH = GetLLH(DataHist[SampleNum], DrawHist, DrawW2Hist);
1261  llh_data_draw[SampleNum] += DataDrawLLH;
1262  total_llh_data_draw_temp += DataDrawLLH;
1263 
1264  // Likelihood between drawn histogram and fluctuated drawn histogram
1265  const double DrawFlucDrawLLH = GetLLH(FluctDrawHist[SampleNum], DrawHist, DrawW2Hist);
1266  llh_drawfluc_draw[SampleNum] += DrawFlucDrawLLH;
1267  total_llh_drawfluc_draw_temp += DrawFlucDrawLLH;
1268 
1269  // Likelihood between drawn histogram and fluctuated posterior predictive distribution
1270  const double PredFlucDrawLLH = GetLLH(FluctHist[SampleNum], DrawHist, DrawW2Hist);
1271  llh_predfluc_draw[SampleNum] += PredFlucDrawLLH;
1272  total_llh_predfluc_draw_temp += PredFlucDrawLLH;
1273 
1274 //Rate Based p-value
1275  // Likelihood between the drawn histogram and the data
1276  const double RateDataDrawLLH = SampleHandler->GetTestStatLLH(NoOverflowIntegral(DataHist[SampleNum]), NoOverflowIntegral(DrawHist), NoOverflowIntegral(DrawW2Hist));
1277  llh_rate_data_draw[SampleNum] += RateDataDrawLLH;
1278  total_llh_rate_data_draw_temp += RateDataDrawLLH;
1279 
1280  // Likelihood between drawn histogram and fluctuated posterior predictive distribution using rate
1281  const double RatePredFlucDrawLLH = SampleHandler->GetTestStatLLH(NoOverflowIntegral(FluctHist[SampleNum]), NoOverflowIntegral(DrawHist), NoOverflowIntegral(DrawW2Hist));
1282  llh_rate_predfluc_draw[SampleNum] += RatePredFlucDrawLLH;
1283  total_llh_rate_predfluc_draw_temp += RatePredFlucDrawLLH;
1284 
1285 // All LLH below are for validation reason but not used for final P-Value
1286  // Likelihood between the fluctuated drawn histogram and the data
1287  const double DataDrawFlucLLH = GetLLH(DataHist[SampleNum], FluctDrawHist[SampleNum], DrawW2Hist);
1288  llh_data_drawfluc[SampleNum] += DataDrawFlucLLH;
1289  total_llh_data_drawfluc_temp += DataDrawFlucLLH;
1290 
1291  // Likelihood between the drawn histogram and the data
1292  const double DataPredFlucLLH = GetLLH(DataHist[SampleNum], FluctHist[SampleNum], W2MeanHist[SampleNum]);
1293  llh_data_predfluc[SampleNum] += DataPredFlucLLH;
1294  total_llh_data_predfluc_temp += DataPredFlucLLH;
1295 
1296  // Likelihood between the drawn hist and the Posterior Predictive
1297  const double DrawPredLLH = GetLLH(DrawHist, MeanHist[SampleNum], W2MeanHist[SampleNum]);
1298  llh_draw_pred[SampleNum] += DrawPredLLH;
1299  total_llh_draw_pred_temp += DrawPredLLH;
1300 
1301  // Likelihood between fluctuated drawn and predictive
1302  const double DrawFlucPredLLH = GetLLH(FluctDrawHist[SampleNum], MeanHist[SampleNum], W2MeanHist[SampleNum]);
1303  llh_drawfluc_pred[SampleNum] += DrawFlucPredLLH;
1304  total_llh_drawfluc_pred_temp += DrawFlucPredLLH;
1305 
1306  // Likelihood between drawn histogram and fluctuated drawn histogram
1307  const double DrawFlucPredFlucLLH = GetLLH(FluctDrawHist[SampleNum], FluctHist[SampleNum], W2MeanHist[SampleNum]);
1308  llh_drawfluc_predfluc[SampleNum] += DrawFlucPredFlucLLH;
1309  total_llh_drawfluc_predfluc_temp += DrawFlucPredFlucLLH;
1310 
1311  // Likelihood between the fluctuated drawn histogram and the posterior predictive
1312  const double PredFlucPredLLH = GetLLH(FluctHist[SampleNum], MeanHist[SampleNum], W2MeanHist[SampleNum]);
1313  llh_predfluc_pred[SampleNum] += PredFlucPredLLH;
1314  total_llh_predfluc_pred_temp += PredFlucPredLLH;
1315 
1316  // Likelihood between fluctuated data histogram and drawn histogram
1317  const double DataFlucDrawLLH = GetLLH(DataFlucHist[SampleNum], DrawHist, DrawW2Hist);
1318  llh_datafluc_draw[SampleNum] += DataFlucDrawLLH;
1319  total_llh_datafluc_draw_temp += DataFlucDrawLLH;
1320 
1321  lnLHist_Sample_DrawData[SampleNum]->Fill(DataDrawLLH);
1322  lnLHist_Sample_DrawflucDraw[SampleNum]->Fill(DrawFlucDrawLLH);
1323  lnLHist_Sample_PredflucDraw[SampleNum]->Fill(PredFlucDrawLLH);
1324 
1325 // At the end we leave LLH for 1D projections
1326  MakeFluctuatedHistogram(FluctDrawHistProjectX[SampleNum], DrawHistProjectX[SampleNum]);
1327 
1328  // Likelihood between the drawn histogram and the data for muon momentum
1329  const double DataDrawLLH_ProjectX = GetLLH(DataHist_ProjectX[SampleNum], DrawHistProjectX[SampleNum], DrawW2HistProjectX[SampleNum]);
1330  llh_data_draw_ProjectX[SampleNum] += DataDrawLLH_ProjectX;
1331  total_llh_data_draw_ProjectX_temp += DataDrawLLH_ProjectX;
1332 
1333  const double DrawFlucDrawLLH_ProjectX = GetLLH(FluctDrawHistProjectX[SampleNum], DrawHistProjectX[SampleNum], DrawW2HistProjectX[SampleNum]);
1334  llh_drawfluc_draw_ProjectX[SampleNum] += DrawFlucDrawLLH_ProjectX;
1335  total_llh_drawfluc_draw_ProjectX_temp += DrawFlucDrawLLH_ProjectX;
1336 
1337  //KS: This might seem complicated but we make X and Y projection for each sample. Then we add this to the Violin plot making nice Gaussian in each kineatmical bin of x and y axis
1338  FastViolinFill(ViolinHists_ProjectX[SampleNum], DrawHistProjectX[SampleNum]);
1339  FastViolinFill(ViolinHists_ProjectY[SampleNum], DrawHistProjectY[SampleNum]);
1340  } // End loop over samples (still looping throws)
1341 
1342  // Delete the temporary histograms
1343  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
1344  {
1345  delete FluctHist[SampleNum];
1346  delete FluctDrawHist[SampleNum];
1347  delete DataFlucHist[SampleNum];
1348  delete FluctDrawHistProjectX[SampleNum];
1349  delete DrawHistProjectX[SampleNum];
1350  delete DrawHistProjectY[SampleNum];
1351  delete DrawW2HistProjectX[SampleNum];
1352  }
1353 
1354  total_llh_data_draw = total_llh_data_draw_temp;
1355  total_llh_drawfluc_draw = total_llh_drawfluc_draw_temp;
1356  total_llh_predfluc_draw = total_llh_predfluc_draw_temp;
1357 
1358  total_llh_rate_data_draw = total_llh_rate_data_draw_temp;
1359  total_llh_rate_predfluc_draw = total_llh_rate_predfluc_draw_temp;
1360 
1361  total_llh_data_drawfluc = total_llh_data_drawfluc_temp;
1362  total_llh_data_predfluc = total_llh_data_predfluc_temp;
1363  total_llh_draw_pred = total_llh_draw_pred_temp;
1364  total_llh_drawfluc_pred = total_llh_drawfluc_pred_temp;
1365  total_llh_drawfluc_predfluc = total_llh_drawfluc_predfluc_temp;
1366  total_llh_predfluc_pred = total_llh_predfluc_pred_temp;
1367  total_llh_datafluc_draw = total_llh_datafluc_draw_temp;
1368 
1369  total_llh_data_draw_ProjectX = total_llh_data_draw_ProjectX_temp;
1370  total_llh_drawfluc_draw_ProjectX = total_llh_drawfluc_draw_ProjectX_temp;
1371 
1372  // Add LLH penalties from the systematics to the LLH that use the drawn histogram
1376  //Rate based
1379 
1384 
1387 
1392 
1395 
1397 
1399 
1400  // Also save to arrays to make sure we have the utmost super accuracy
1401  LLH_PredFluc_V[i] = total_llh_predfluc_draw;
1402  LLH_DataDraw_V[i] = total_llh_data_draw;
1403  LLH_DrawFlucDraw_V[i] = total_llh_drawfluc_draw;
1404 
1405  // Write to the output tree
1406  OutputTree->Fill();
1407  } // End loop over throws
1408 
1409  AveragePenalty = AveragePenalty/double(nThrows);
1410  MACH3LOG_INFO("Average LLH penalty over toys is {:.2f}", AveragePenalty);
1411  // Calculate exact p-value instead of binned
1412  unsigned int Accept_PredFluc = 0;
1413  unsigned int Accept_DrawFluc = 0;
1414  for (unsigned int i = 0; i < nThrows; ++i)
1415  {
1416  if (LLH_DataDraw_V[i] > LLH_DrawFlucDraw_V[i]) Accept_DrawFluc++;
1417  if (LLH_DataDraw_V[i] > LLH_PredFluc_V[i]) Accept_PredFluc++;
1418  }
1419  const double pvalue_DrawFluc = double(Accept_DrawFluc)/double(nThrows);
1420  const double pvalue_PredFluc = double(Accept_PredFluc)/double(nThrows);
1421 
1422  MACH3LOG_INFO("Calculated exact p-value using Fluctuation of Draw: {:.2f}", pvalue_DrawFluc);
1423  MACH3LOG_INFO("Calculated exact p-value using Fluctuation of Prediction: {:.2f}", pvalue_PredFluc);
1424 }
void FastViolinFill(TH2D *violin, TH1D *hist_1d)
KS: Fill Violin histogram with entry from a toy.
std::vector< double > llh_data_draw_ProjectX
Projection X (most likely muon momentum) of LLH.
std::vector< double > llh_predfluc_draw
Fluctuated Predictive vs Draw.
double total_llh_predfluc_pred
Fluctuated Predictive vs Predictive.
double total_llh_drawfluc_draw_ProjectX
Fluctuated Draw vs Draw for projection X (most likely muon momentum)
double total_llh_data_draw
Data vs Draw.
double total_llh_rate_predfluc_draw
Fluctuated Predictive vs Draw using Rate.
std::vector< double > llh_data_predfluc
Data vs Fluctuated Predictive.
std::vector< double > llh_predfluc_pred
Fluctuated Predictive vs Predictive.
double total_llh_draw_pred
Draw vs Predictive.
std::vector< double > llh_drawfluc_draw
Fluctuated Draw vs Draw.
double total_llh_data_draw_ProjectX
Data vs Draw for projection X (most likely muon momentum)
std::vector< double > llh_drawfluc_predfluc
Fluctuated Draw vs Fluctuated Predictive.
std::vector< double > llh_data_draw
Data vs Draw.
double total_llh_data_drawfluc
Data vs Fluctuated Draw.
double total_llh_drawfluc_draw
Fluctuated Draw vs Draw.
std::vector< double > llh_draw_pred
Draw vs Predictive.
double total_llh_predfluc_draw
Fluctuated Predictive vs Draw.
std::vector< double > llh_drawfluc_draw_ProjectX
std::vector< double > llh_data_drawfluc
Data vs Fluctuated Draw.
double total_llh_drawfluc_pred
Fluctuated Draw vs Predictive.
std::vector< double > llh_rate_predfluc_draw
Fluctuated Predictive vs Draw using rate only.
double total_llh_rate_data_draw
Rate Data vs Draw.
std::vector< double > llh_drawfluc_pred
Fluctuated Draw vs Predictive.
std::vector< double > llh_datafluc_draw
Fluctuated Data vs Draw.
void MakeFluctuatedHistogram(TH1D *FluctHist, TH1D *PolyHist)
Make Poisson fluctuation of TH1D hist.
std::vector< double > llh_rate_data_draw
Data vs Draw using rate only.
double total_llh_data_predfluc
Data vs Fluctuated Predictive.
double llh_penalty
LLH penalty for each throw.
double total_llh_drawfluc_predfluc
Fluctuated Draw vs Fluctuated Predictive.
double total_llh_datafluc_draw
Fluctuated Data vs Draw.
void PrintProgressBar(const Long64_t Done, const Long64_t All)
KS: Simply print progress bar.
Definition: Monitor.cpp:229

◆ MakeCutEventRate()

void SampleSummary::MakeCutEventRate ( TH1D *  Histogram,
const double  DataRate 
)
inlineprivate

Make the 1D Event Rate Hist.

Definition at line 1506 of file SampleSummary.cpp.

1506  {
1507 // ****************
1508  // For the event rate histogram add a TLine to the data rate
1509  auto TempLine = std::make_unique<TLine>(DataRate, Histogram->GetMinimum(), DataRate, Histogram->GetMaximum());
1510  TempLine->SetLineColor(kRed);
1511  TempLine->SetLineWidth(2);
1512  // Also fit a Gaussian because why not?
1513  TF1 *Fitter = new TF1("Fit", "gaus", Histogram->GetBinLowEdge(1), Histogram->GetBinLowEdge(Histogram->GetNbinsX()+1));
1514  Histogram->Fit(Fitter, "RQ");
1515  Fitter->SetLineColor(kRed-5);
1516  // Calculate a p-value
1517  double Above = 0.0;
1518  for (int z = 0; z < Histogram->GetNbinsX(); ++z) {
1519  const double xvalue = Histogram->GetBinCenter(z+1);
1520  if (xvalue >= DataRate) {
1521  Above += Histogram->GetBinContent(z+1);
1522  }
1523  }
1524  const double pvalue = Above/Histogram->Integral();
1525  auto Legend = std::make_unique<TLegend>(0.4, 0.75, 0.98, 0.90);
1526  Legend->SetFillColor(0);
1527  Legend->SetFillStyle(0);
1528  Legend->SetLineWidth(0);
1529  Legend->SetLineColor(0);
1530  Legend->AddEntry(TempLine.get(), Form("Data, %.0f, p-value=%.2f", DataRate, pvalue), "l");
1531  Legend->AddEntry(Histogram, Form("MC, #mu=%.1f#pm%.1f", Histogram->GetMean(), Histogram->GetRMS()), "l");
1532  Legend->AddEntry(Fitter, Form("Gauss, #mu=%.1f#pm%.1f", Fitter->GetParameter(1), Fitter->GetParameter(2)), "l");
1533  std::string TempTitle = std::string(Histogram->GetName());
1534  TempTitle += "_canv";
1535  TCanvas *TempCanvas = new TCanvas(TempTitle.c_str(), TempTitle.c_str(), 1024, 1024);
1536  TempCanvas->SetGridx();
1537  TempCanvas->SetGridy();
1538  TempCanvas->SetRightMargin(0.03);
1539  TempCanvas->SetBottomMargin(0.08);
1540  TempCanvas->SetLeftMargin(0.10);
1541  TempCanvas->SetTopMargin(0.06);
1542  TempCanvas->cd();
1543  Histogram->Draw();
1544  TempLine->Draw("same");
1545  Fitter->Draw("same");
1546  Legend->Draw("same");
1547  TempCanvas->Write();
1548  Histogram->Write();
1549 
1550  delete TempCanvas;
1551  delete Fitter;
1552 }

◆ MakeCutLLH()

void SampleSummary::MakeCutLLH ( )
inlineprivate

Make the cut LLH histogram.

Definition at line 1428 of file SampleSummary.cpp.

1428  {
1429 // *******************
1430  Outputfile->cd();
1431  MakeCutLLH1D(lnLHist.get());
1435 
1440 }
void Get2DBayesianpValue(TH2D *Histogram)
Calculates the 2D Bayesian p-value and generates a visualization.
void MakeCutLLH1D(TH1D *Histogram, double llh_ref=-999)

◆ MakeCutLLH1D()

void SampleSummary::MakeCutLLH1D ( TH1D *  Histogram,
double  llh_ref = -999 
)
inlineprivate

Definition at line 1444 of file SampleSummary.cpp.

1444  {
1445 // ****************
1446  const double TotalIntegral = Histogram->Integral();
1447  double Above = 0.0;
1448  // Get the LLH reference from total llh or some reference histogram
1449  double llh_reference = 0.0;
1450  if (llh_ref >= 0) {
1451  llh_reference = llh_ref;
1452  } else {
1453  llh_reference = llh_total;
1454  }
1455  for (int i = 0; i < Histogram->GetXaxis()->GetNbins(); ++i) {
1456  const double xvalue = Histogram->GetBinCenter(i+1);
1457  if (xvalue >= llh_reference) {
1458  Above += Histogram->GetBinContent(i+1);
1459  }
1460  }
1461  const double pvalue = Above/TotalIntegral;
1462  std::stringstream ss;
1463  ss << int(Above) << "/" << int(TotalIntegral) << "=" << pvalue;
1464  Histogram->SetTitle((std::string(Histogram->GetTitle())+"_"+ss.str()).c_str());
1465 
1466  // Write a TCanvas and make a line and a filled histogram
1467  auto TempLine = std::make_unique<TLine>(llh_reference , Histogram->GetMinimum(), llh_reference, Histogram->GetMaximum());
1468  TempLine->SetLineColor(kBlack);
1469  TempLine->SetLineWidth(2);
1470 
1471  // Make the fill histogram
1472  TH1D *TempHistogram = static_cast<TH1D*>(Histogram->Clone());
1473  TempHistogram->SetFillStyle(1001);
1474  TempHistogram->SetFillColor(kRed);
1475  for (int i = 0; i < TempHistogram->GetNbinsX(); ++i) {
1476  if (TempHistogram->GetBinCenter(i+1) < llh_reference) {
1477  TempHistogram->SetBinContent(i+1, 0.0);
1478  }
1479  }
1480 
1481  auto Legend = std::make_unique<TLegend>(0.6, 0.6, 0.9, 0.9);
1482  Legend->SetFillColor(0);
1483  Legend->SetFillStyle(0);
1484  Legend->SetLineWidth(0);
1485  Legend->SetLineColor(0);
1486  Legend->AddEntry(TempLine.get(), Form("Reference LLH, %.0f, p-value=%.2f", llh_reference, pvalue), "l");
1487  Legend->AddEntry(Histogram, Form("LLH, #mu=%.1f#pm%.1f", Histogram->GetMean(), Histogram->GetRMS()), "l");
1488  std::string Title = Histogram->GetName();
1489  Title += "_canv";
1490  TCanvas *TempCanvas = new TCanvas(Title.c_str(), Title.c_str(), 1024, 1024);
1491  TempCanvas->SetGridx();
1492  TempCanvas->SetGridy();
1493  Histogram->Draw();
1494  TempHistogram->Draw("same");
1495  TempLine->Draw("same");
1496  Legend->Draw("same");
1497 
1498  TempCanvas->Write();
1499 
1500  delete TempHistogram;
1501  delete TempCanvas;
1502 }
double llh_total
Total LLH for the posterior predictive distribution.

◆ MakeFluctuatedHistogram() [1/2]

void SampleSummary::MakeFluctuatedHistogram ( TH1D *  FluctHist,
TH1D *  PolyHist 
)
inlineprivate

Make Poisson fluctuation of TH1D hist.

Definition at line 2177 of file SampleSummary.cpp.

2177  {
2178 // ****************
2179  if(StandardFluctuation) MakeFluctuatedHistogramStandard(FluctHist, PolyHist, rnd.get());
2180  else MakeFluctuatedHistogramAlternative(FluctHist, PolyHist, rnd.get());
2181 }
void MakeFluctuatedHistogramAlternative(TH1D *FluctHist, TH1D *PolyHist, TRandom3 *rand)
Make Poisson fluctuation of TH1D hist using slow method which is only for cross-check.
void MakeFluctuatedHistogramStandard(TH1D *FluctHist, TH1D *PolyHist, TRandom3 *rand)
Make Poisson fluctuation of TH1D hist using default fast method.

◆ MakeFluctuatedHistogram() [2/2]

void SampleSummary::MakeFluctuatedHistogram ( TH2Poly *  FluctHist,
TH2Poly *  PolyHist 
)
inlineprivate

Make Poisson fluctuation of TH2Poly hist.

Definition at line 2185 of file SampleSummary.cpp.

2185  {
2186 // ****************
2187  if(StandardFluctuation) MakeFluctuatedHistogramStandard(FluctHist, PolyHist, rnd.get());
2188  else MakeFluctuatedHistogramAlternative(FluctHist, PolyHist, rnd.get());
2189 }

◆ MakePredictive()

void SampleSummary::MakePredictive ( )
inlineprivate

Finalise the distributions from the thrown samples.

Definition at line 975 of file SampleSummary.cpp.

975  {
976 // *******************
977  // First make the projection on the z axis of the TH3D* for every pmu cosmu bin
978  double llh_total_temp = 0.0;
979 
980  // Loop over the samples
981  #ifdef MULTITHREAD
982  #pragma omp parallel for reduction(+:llh_total_temp)
983  #endif
984  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
985  {
986  // Skip disabled samples
987  if (DataHist[SampleNum] == nullptr || NoOverflowIntegral(DataHist[SampleNum]) == 0) continue;
988 
989  // Count the -2LLH for each histogram
990  double negLogL_Mean = 0.0;
991 
992  // Loop over each pmu cosmu bin
993  for (int j = 1; j < maxBins[SampleNum]+1; ++j)
994  {
995  TH1D *Projection = PosteriorHist[SampleNum][j].get();
996  TH1D *W2Projection = w2Hist[SampleNum][j].get();
997 
998  // Data content for the j,kth bin
999  const double nData = DataHist[SampleNum]->GetBinContent(j);
1000 
1001  // Get the mean for this projection for all the samples
1002  // This is the mean prediction for this given j,k bin
1003  const double nMean = Projection->GetMean();
1004  const double nMeanError = Projection->GetRMS();
1005  const double nMode = Projection->GetBinCenter(Projection->GetMaximumBin());
1006  const double nModeError = GetModeError(Projection);
1007 
1008  const double nW2Mean = W2Projection->GetMean();
1009  const double nW2Mode = W2Projection->GetBinCenter(W2Projection->GetMaximumBin());
1010 
1011  double TempLLH_Mean = 0.0;
1012  double TempLLH_Mode = 0.0;
1013 
1014  //KS:Get LLH contribution getTestStatLLH can calculate Barlow Beeston/IceCube or Poisson
1015  TempLLH_Mean = SampleHandler->GetTestStatLLH(nData, nMean, nW2Mean);
1016  TempLLH_Mode = SampleHandler->GetTestStatLLH(nData, nMode, nW2Mode);
1017 
1018  // Increment -2LLH
1019  //KS: do times 2 because banff reports chi2
1020  negLogL_Mean += 2*TempLLH_Mean;
1021 
1022  // Set the content and error to the mean in the bin
1023  MeanHist[SampleNum]->SetBinContent(j, MeanHist[SampleNum]->GetBinContent(j)+nMean);
1024  // KS: This -1 is only needed for root older than 6.18 for more see https://t2k-experiment.slack.com/archives/CU9CBG6NS/p1714551365661589
1025  MeanHist[SampleNum]->SetBinError(j, nMeanError);
1026 
1027  if(DoBetaParam)
1028  {
1029  TH1D *BetaTemp = BetaHist[SampleNum][j].get();
1030  const double nBetaMean = BetaTemp->GetMean();
1031  const double nBetaMeanError = BetaTemp->GetRMS();
1032  //KS: Here we modify predictions by beta parameter from Barlow-Beeston
1033  MeanHistCorrected[SampleNum]->SetBinContent(j, MeanHistCorrected[SampleNum]->GetBinContent(j)+nMean*nBetaMean);
1034  //KS: Use error propagation to calcuate error
1035  const double ErrorTemp = std::sqrt( (nBetaMean*nMeanError) * (nBetaMean*nMeanError) + (nMean*nBetaMeanError) * (nMean*nBetaMeanError));
1036  // KS: This -1 is only needed for root older than 6.18 for more see https://t2k-experiment.slack.com/archives/CU9CBG6NS/p1714551365661589
1037  MeanHistCorrected[SampleNum]->SetBinError(j, ErrorTemp);
1038  }
1039  // Set the content to the mode in the bin
1040  ModeHist[SampleNum]->SetBinContent(j, ModeHist[SampleNum]->GetBinContent(j)+nMode);
1041  // KS: This -1 is only needed for root older than 6.18 for more see https://t2k-experiment.slack.com/archives/CU9CBG6NS/p1714551365661589
1042  ModeHist[SampleNum]->SetBinError(j, nModeError);
1043  // Set the content to the mean in the bin
1044  W2MeanHist[SampleNum]->SetBinContent(j, W2MeanHist[SampleNum]->GetBinContent(j)+nW2Mean);
1045  // Set the content to the mode in the bin
1046  W2ModeHist[SampleNum]->SetBinContent(j, W2ModeHist[SampleNum]->GetBinContent(j)+nW2Mode);
1047 
1048  // Set the mean and average LLH for this given bin
1049  // Can use these hists to see where the largest -2LLH hists come from
1050  lnLHist_Mean[SampleNum]->SetBinContent(j, 2.0*TempLLH_Mean);
1051  lnLHist_Mode[SampleNum]->SetBinContent(j, 2.0*TempLLH_Mode);
1052 
1053  lnLHist_Mean1D[SampleNum]->Fill(2.0*TempLLH_Mean);
1054  lnLHist_Mode1D[SampleNum]->Fill(2.0*TempLLH_Mode);
1055  } // End loop over bins
1056  if(DoByModePlots)
1057  {
1058  for (int j = 0; j < Modes->GetNModes()+1; j++)
1059  {
1060  // Loop over each pmu cosmu bin
1061  for (int i = 1; i < maxBins[SampleNum]+1; ++i)
1062  {
1063  // Make the posterior/prior predictive projection on z
1064  // The z axis of Predictive is the bin content
1065  // Essentially zooming in on one bin and looking at the mean and mode of that bin
1066  TH1D *Projection = PosteriorHist_ByMode[SampleNum][j][i];
1067 
1068  // Get the mean for this projection for all the samples
1069  const double nMean = Projection->GetMean();
1070  const double nMeanError = Projection->GetRMS();
1071 
1072  // Set the content and error to the mean in the bin
1073  MeanHist_ByMode[SampleNum][j]->SetBinContent(i, MeanHist_ByMode[SampleNum][j]->GetBinContent(i)+nMean);
1074  // KS: This -1 is only needed for root older than 6.18 for more see https://t2k-experiment.slack.com/archives/CU9CBG6NS/p1714551365661589
1075  MeanHist_ByMode[SampleNum][j]->SetBinError(i, nMeanError);
1076  } // End loop over bins
1077  }
1078  }
1079  llh_total_temp += negLogL_Mean;
1080  } // End loop over samples
1081 
1082  // This is not multithreaded as due to ProjectPoly it is not safe
1083  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
1084  {
1085  // Skip disabled samples
1086  if (DataHist[SampleNum] == nullptr || NoOverflowIntegral(DataHist[SampleNum]) == 0) continue;
1087 
1088  //KS:: Might consider caching it as we use it once agian much later
1089  TH1D *MeanProjectX = ProjectPoly(MeanHist[SampleNum], true, SampleNum, true);
1090  TH1D *W2MeanProjectX = ProjectPoly(W2MeanHist[SampleNum], true, SampleNum);
1091  // Loop over each pmu bin for 1D projection
1092  for (int j = 1; j <= lnLHist_Mean_ProjectX[SampleNum]->GetXaxis()->GetNbins(); ++j)
1093  {
1094  // Data content for the j,kth bin
1095  const double nData = DataHist_ProjectX[SampleNum]->GetBinContent(j);
1096  const double nMean = MeanProjectX->GetBinContent(j);
1097  const double nW2Mean = W2MeanProjectX->GetBinContent(j);
1098 
1099  double TempLLH_Mean = 0.0;
1100  TempLLH_Mean = SampleHandler->GetTestStatLLH(nData, nMean, nW2Mean);
1101 
1102  //KS: do times 2 because banff reports chi2
1103  lnLHist_Mean_ProjectX[SampleNum]->SetBinContent(j, 2.0*TempLLH_Mean);
1104  }// End loop over bins
1105 
1106  delete MeanProjectX;
1107  delete W2MeanProjectX;
1108  } // End loop over samples
1109 
1110  llh_total = llh_total_temp;
1111  // Now we have our posterior predictive histogram and it's LLH
1112  MACH3LOG_INFO("Prior/Posterior predictive LLH mean (sample only) = {:.2f}", llh_total);
1113  std::stringstream ss;
1114  ss << llh_total;
1115  lnLHist->SetTitle((std::string(lnLHist->GetTitle())+"_"+ss.str()).c_str());
1116 
1117  // Now make the fluctuated hists of the MeanHist and ModeHist
1118  MakeChi2Hists();
1119 
1120  // Get the 1D LLH dists
1121  MakeCutLLH();
1122 } // End MakePredictive() function
double GetModeError(TH1D *hpost)
Get the mode error from a TH1D.
void MakeChi2Hists()
Make the fluctuated histograms (2D and 1D) for the chi2s Essentially taking the MCMC draws and calcul...
void MakeCutLLH()
Make the cut LLH histogram.

◆ PlotBetaParameters()

void SampleSummary::PlotBetaParameters ( )
inlineprivate

KS: In Barlow Beeston we have Beta Parameters which scale generated MC.

Definition at line 1607 of file SampleSummary.cpp.

1607  {
1608 // ****************
1609  // Make a new directory
1610  TDirectory *BetaDir = Outputfile->mkdir("BetaParameters");
1611  BetaDir->cd();
1612 
1613  int originalErrorLevel = gErrorIgnoreLevel;
1614 
1615  //To avoid Warning in <Fit>: Fit data is empty
1616  gErrorIgnoreLevel = kFatal;
1617 
1618  MACH3LOG_INFO("Writing Beta parameters");
1619  std::vector<TDirectory *> DirBeta(nSamples);
1620  for (int i = 0; i < nSamples; ++i)
1621  {
1622  // Make a new directory
1623  DirBeta[i] = BetaDir->mkdir((SampleNames[i]).c_str());
1624  DirBeta[i]->cd();
1625 
1626  // Loop over each pmu cosmu bin
1627  for (int j = 1; j < maxBins[i]+1; ++j)
1628  {
1629  const double data = DataHist[i]->GetBinContent(j);
1630  const double mc = NominalHist[i]->GetBinContent(j);
1631  const double w2 = W2NomHist[i]->GetBinContent(j);
1632 
1633  const double BetaPrior = GetBetaParameter(data, mc, w2, likelihood);
1634 
1635  auto TempLine = std::unique_ptr<TLine>(new TLine(BetaPrior, BetaHist[i][j]->GetMinimum(), BetaPrior, BetaHist[i][j]->GetMaximum()));
1636  TempLine->SetLineColor(kRed);
1637  TempLine->SetLineWidth(2);
1638 
1639  // Also fit a Gaussian because why not?
1640  TF1 *Fitter = new TF1("Fit", "gaus", BetaHist[i][j]->GetBinLowEdge(1), BetaHist[i][j]->GetBinLowEdge(BetaHist[i][j]->GetNbinsX()+1));
1641  BetaHist[i][j]->Fit(Fitter, "RQ");
1642  Fitter->SetLineColor(kRed-5);
1643 
1644  auto Legend = std::make_unique<TLegend>(0.4, 0.75, 0.98, 0.90);
1645  Legend->SetFillColor(0);
1646  Legend->SetFillStyle(0);
1647  Legend->SetLineWidth(0);
1648  Legend->SetLineColor(0);
1649  Legend->AddEntry(TempLine.get(), Form("Prior #mu=%.4f, N_{data}=%.0f", BetaPrior, data), "l");
1650  Legend->AddEntry(BetaHist[i][j].get(), Form("Post, #mu=%.4f#pm%.4f", BetaHist[i][j]->GetMean(), BetaHist[i][j]->GetRMS()), "l");
1651  Legend->AddEntry(Fitter, Form("Gauss, #mu=%.4f#pm%.4f", Fitter->GetParameter(1), Fitter->GetParameter(2)), "l");
1652  std::string TempTitle = std::string(BetaHist[i][j]->GetName());
1653 
1654  TempTitle += "_canv";
1655  TCanvas *TempCanvas = new TCanvas(TempTitle.c_str(), TempTitle.c_str(), 1024, 1024);
1656  TempCanvas->SetGridx();
1657  TempCanvas->SetGridy();
1658  TempCanvas->SetRightMargin(0.03);
1659  TempCanvas->SetBottomMargin(0.08);
1660  TempCanvas->SetLeftMargin(0.10);
1661  TempCanvas->SetTopMargin(0.06);
1662  TempCanvas->cd();
1663  BetaHist[i][j]->Draw();
1664  TempLine->Draw("same");
1665  Fitter->Draw("same");
1666  Legend->Draw("same");
1667  TempCanvas->Write();
1668  BetaHist[i][j]->Write();
1669 
1670  delete TempCanvas;
1671  delete Fitter;
1672  }
1673  DirBeta[i]->Write();
1674  delete DirBeta[i];
1675  }
1676  BetaDir->Write();
1677  delete BetaDir;
1678 
1679  gErrorIgnoreLevel = originalErrorLevel;
1680  Outputfile->cd();
1681 }
std::vector< std::string > SampleNames
name for each sample

◆ PrepareOutput()

void SampleSummary::PrepareOutput ( )
inlineprivate

KS: Prepare output tree and necessary variables.

Definition at line 554 of file SampleSummary.cpp.

554  {
555 // **********************
556  // Make the output file (MakePosterioPredictive call writes to this)
557  std::string TempString = OutputName;
558  TempString.replace(TempString.find(".root"), 5, std::string("_procsW2.root"));
559  Outputfile = M3::Open(TempString, "RECREATE", __FILE__, __LINE__);
560 
561  // The array of doubles we write to the TTree
562  // Data vs Draw
563  llh_data_draw.resize(nSamples);
564  // Fluctuated Draw vs Draw
565  llh_drawfluc_draw.resize(nSamples);
566  // Fluctuated Predicitve vs Draw
567  llh_predfluc_draw.resize(nSamples);
568 
569  // Data vs Draw using Rate
571  // Data vs Fluctuated Predictive using Rate
573 
574  // Data vs Fluctuated Draw
575  llh_data_drawfluc.resize(nSamples);
576  // Data vs Fluctuated Predictive
577  llh_data_predfluc.resize(nSamples);
578  // Draw vs Predictive
579  llh_draw_pred.resize(nSamples);
580  // Fluctuated Draw vs Predictive
581  llh_drawfluc_pred.resize(nSamples);
582  // Fluctuated Draw vs Fluctuated Predictive
584 
585  // Fluctuated Predictive vs Predictive
586  llh_predfluc_pred.resize(nSamples);
587  // Fluctuated Data vs Draw
588  llh_datafluc_draw.resize(nSamples);
589 
590  // Data vs Draw for 1D projection
593 
594  // The output tree we're going to write to
595  OutputTree = new TTree("LLH_draws", "LLH_draws");
596  SampleNames.resize(nSamples);
597  // Loop over the samples and set the addresses of the variables to write to file
598  for (int i = 0; i < nSamples; ++i)
599  {
600  // Get the name
601  std::string SampleName = SampleHandler->GetSampleTitle(i);
602  // Strip out spaces
603  while (SampleName.find(" ") != std::string::npos) {
604  SampleName.replace(SampleName.find(" "), 1, std::string("_"));
605  }
606  SampleNames[i] = SampleName;
607  //CW: Also strip out - signs because it messes up TBranches
608  while (SampleName.find("-") != std::string::npos) {
609  SampleName.replace(SampleName.find("-"), 1, std::string("_"));
610  }
611 // All LLH below are used for actual p-value calculations
612  OutputTree->Branch((SampleName+"_data_draw").c_str(), &llh_data_draw[i]);
613  OutputTree->Branch((SampleName+"_drawfluc_draw").c_str(), &llh_drawfluc_draw[i]);
614  OutputTree->Branch((SampleName+"_predfluc_draw").c_str(), &llh_predfluc_draw[i]);
615 
616 // All LLH below are used for actual p-value calculations however using rate only
617  OutputTree->Branch((SampleName+"_rate_data_draw").c_str(), &llh_rate_data_draw[i]);
618  OutputTree->Branch((SampleName+"_rate_predfluc_draw").c_str(), &llh_rate_predfluc_draw[i]);
619 
620 // All LLH below are for validation reason but not used for final P-Value
621  OutputTree->Branch((SampleName+"_data_drawfluc").c_str(), &llh_data_drawfluc[i]);
622  OutputTree->Branch((SampleName+"_data_predfluc").c_str(), &llh_data_predfluc[i]);
623  OutputTree->Branch((SampleName+"_draw_pred").c_str(), &llh_draw_pred[i]);
624  OutputTree->Branch((SampleName+"_drawfluc_pred").c_str(), &llh_drawfluc_pred[i]);
625  OutputTree->Branch((SampleName+"_drawfluc_predfluc").c_str(), &llh_drawfluc_predfluc[i]);
626  OutputTree->Branch((SampleName+"_predfluc_pred").c_str(), &llh_predfluc_pred[i]);
627  OutputTree->Branch((SampleName+"_datafluc_draw").c_str(), &llh_datafluc_draw[i]);
628 
629 // All LLH below are used for calcauting P-Value but using 1D projections
630  OutputTree->Branch((SampleName+"_data_draw_ProjectX").c_str(), &llh_data_draw_ProjectX[i]);
631  OutputTree->Branch((SampleName+"_drawfluc_draw_ProjectX").c_str(), &llh_drawfluc_draw_ProjectX[i]);
632  }
633 //All LLH below are used for actual p-value calculations
634  OutputTree->Branch("LLH_Penalty", &llh_penalty);
635  OutputTree->Branch("Total_LLH_Data_Draw", &total_llh_data_draw);
636  OutputTree->Branch("Total_LLH_DrawFluc_Draw", &total_llh_drawfluc_draw);
637  OutputTree->Branch("Total_LLH_PredFluc_Draw", &total_llh_predfluc_draw);
638 
639 // All LLH below are used for actual p-value calculations however using rate only
640  OutputTree->Branch("Total_LLH_Rate_PredFluc_Draw", &total_llh_rate_predfluc_draw);
641 
642 //All LLH below are for validation reason but not used for final P-Value
643  OutputTree->Branch("Total_LLH_Data_DrawFluc", &total_llh_data_drawfluc);
644  OutputTree->Branch("Total_LLH_Data_PredFluc", &total_llh_data_predfluc);
645  OutputTree->Branch("Total_LLH_Draw_Pred", &total_llh_draw_pred);
646  OutputTree->Branch("Total_LLH_DrawFluc_Pred", &total_llh_drawfluc_pred);
647  OutputTree->Branch("Total_LLH_DrawFluc_PredFluc", &total_llh_drawfluc_predfluc);
648  OutputTree->Branch("Total_LLH_PredFluc_Pred", &total_llh_predfluc_pred);
649  OutputTree->Branch("Total_LLH_DataFluc_Draw", &total_llh_datafluc_draw);
650 
651 //All LLH below are used for calcauting P-Value but 1D projections
652  OutputTree->Branch("total_llh_data_draw_ProjectX", &total_llh_data_draw_ProjectX);
653  OutputTree->Branch("total_llh_drawfluc_draw_ProjectX", &total_llh_drawfluc_draw_ProjectX);
654 
655  Outputfile->cd();
656  Dir.resize(nSamples);
657  for (int i = 0; i < nSamples; ++i)
658  {
659  // Make a new directory
660  Dir[i] = Outputfile->mkdir((SampleNames[i]).c_str());
661  }
662 }
std::vector< TDirectory * > Dir
Directory for each sample.
TFile * Open(const std::string &Name, const std::string &Type, const std::string &File, const int Line)
Opens a ROOT file with the given name and mode.

◆ ProjectHist()

TH1D * SampleSummary::ProjectHist ( TH2D *  Histogram,
const bool  ProjectX 
)
inlineprivate

Helper to project TH2D onto axis.

Definition at line 2142 of file SampleSummary.cpp.

2142  {
2143 // ****************
2144  TH1D* Projection = nullptr;
2145  std::string name;
2146  if (ProjectX) {
2147  name = std::string(Histogram->GetName()) + "_x";
2148  Projection = Histogram->ProjectionX(name.c_str(), 1, Histogram->GetYaxis()->GetNbins(), "e");
2149  } else {
2150  name = std::string(Histogram->GetName()) + "_y";
2151  Projection = Histogram->ProjectionY(name.c_str(), 1, Histogram->GetXaxis()->GetNbins(), "e");
2152  }
2153  return Projection;
2154 }

◆ ProjectPoly()

TH1D * SampleSummary::ProjectPoly ( TH2Poly *  Histogram,
const bool  ProjectX,
const int  selection,
const bool  MakeErrorHist = false 
)
inlineprivate

Helper to project TH2Poly onto axis.

Definition at line 2158 of file SampleSummary.cpp.

2158  {
2159 // ****************
2160  std::vector<double> xbins = SampleHandler->ReturnKinematicParameterBinning(M3::int_t(selection), SampleHandler->GetKinVarName(M3::int_t(selection), 0));
2161  std::vector<double> ybins = SampleHandler->ReturnKinematicParameterBinning(M3::int_t(selection), SampleHandler->GetKinVarName(M3::int_t(selection), 1));
2162 
2163  TH1D* Projection = nullptr;
2164  std::string name;
2165  if (ProjectX) {
2166  name = std::string(Histogram->GetName()) + "_x";
2167  Projection = PolyProjectionX(Histogram, name.c_str(), xbins, MakeErrorHist);
2168  } else {
2169  name = std::string(Histogram->GetName()) + "_y";
2170  Projection = PolyProjectionY(Histogram, name.c_str(), ybins, MakeErrorHist);
2171  }
2172  return Projection;
2173 }
TH1D * PolyProjectionX(TObject *poly, const std::string &TempName, const std::vector< double > &xbins, const bool computeErrors)
WP: Poly Projectors.
TH1D * PolyProjectionY(TObject *poly, const std::string &TempName, const std::vector< double > &ybins, const bool computeErrors)
WP: Poly Projectors.

◆ SetLikelihood()

void SampleSummary::SetLikelihood ( const TestStatistic  TestStat)
inline

KS: Set likelihood type.

Definition at line 40 of file SampleSummary.h.

40 { likelihood = TestStat;};

◆ SetNModelParams()

void SampleSummary::SetNModelParams ( const int  nPars)
inline

Set number of model params used for BIC.

Definition at line 42 of file SampleSummary.h.

42 { nModelParams = nPars;};

◆ StudyBIC()

void SampleSummary::StudyBIC ( )
inlineprivate

Study Bayesian Information Criterion (BIC) [13].

Definition at line 2221 of file SampleSummary.cpp.

2221  {
2222 // ****************
2223  //make fancy event rate histogram
2224  double DataRate = 0.0;
2225  double BinsRate = 0.0;
2226  #ifdef MULTITHREAD
2227  #pragma omp parallel for reduction(+:DataRate, BinsRate)
2228  #endif
2229  for (int i = 0; i < nSamples; ++i)
2230  {
2231  if (DataHist[i] == nullptr) continue;
2232  DataRate += NoOverflowIntegral(DataHist[i]);
2233  BinsRate += maxBins[i];
2234  }
2235 
2236  const double EventRateBIC = GetBIC(llh_total, DataRate, nModelParams);
2237  const double BinBasedBIC = GetBIC(llh_total, BinsRate, nModelParams);
2238  MACH3LOG_INFO("Calculated Bayesian Information Criterion using global number of events: {:.2f}", EventRateBIC);
2239  MACH3LOG_INFO("Calculated Bayesian Information Criterion using global number of bins: {:.2f}", BinBasedBIC);
2240  MACH3LOG_INFO("Additional info: nModelParams {} DataRate: {:.2f} BinsRate: {:.2f}", nModelParams, DataRate, BinsRate);
2241 }
double GetBIC(const double llh, const int data, const int nPars)
Get the Bayesian Information Criterion (BIC) or Schwarz information criterion (also SIC,...

◆ StudyDIC()

void SampleSummary::StudyDIC ( )
inlineprivate

KS: Get the Deviance Information Criterion (DIC) [33] [35].

Definition at line 2245 of file SampleSummary.cpp.

2245  {
2246 // ****************
2247  //The posterior mean of the deviance
2248  double Dbar = 0.;
2249 
2250  #ifdef MULTITHREAD
2251  #pragma omp parallel for reduction(+:Dbar)
2252  #endif
2253  for (unsigned int i = 0; i < nThrows; ++i)
2254  {
2255  double LLH_temp = 0.;
2256  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
2257  {
2258  // Get -2*log-likelihood
2259  LLH_temp += GetLLH(DataHist[SampleNum], MCVector[i][SampleNum], W2MCVector[i][SampleNum]);
2260  }
2261  Dbar += LLH_temp;
2262  }
2263  Dbar = Dbar / nThrows;
2264 
2265  // A point estimate of the deviance
2266  const double Dhat = llh_total;
2267 
2268  //Effective number of parameters
2269  const double p_D = std::fabs(Dbar - Dhat);
2270 
2271  //Actual test stat
2272  const double DIC_stat = Dhat + 2 * p_D;
2273  MACH3LOG_INFO("Effective number of parameters following DIC formalism is equal to: {:.2f}", p_D);
2274  MACH3LOG_INFO("DIC test statistic = {:.2f}", DIC_stat);
2275 }

◆ StudyInformationCriterion()

void SampleSummary::StudyInformationCriterion ( M3::kInfCrit  Criterion)
inlineprivate

Information Criterion.

Definition at line 2193 of file SampleSummary.cpp.

2193  {
2194 // ****************
2195  MACH3LOG_INFO("******************************");
2196  switch(Criterion) {
2197  case M3::kInfCrit::kBIC:
2198  // Study Bayesian Information Criterion
2199  StudyBIC();
2200  break;
2201  case M3::kInfCrit::kDIC:
2202  // Study Deviance Information Criterion
2203  StudyDIC();
2204  break;
2205  case M3::kInfCrit::kWAIC:
2206  // Study Watanabe-Akaike information criterion (WAIC)
2207  StudyWAIC();
2208  break;
2210  MACH3LOG_ERROR("kInfCrits is not a valid kInfCrit!");
2211  throw MaCh3Exception(__FILE__, __LINE__);
2212  default:
2213  MACH3LOG_ERROR("UNKNOWN Information Criterion SPECIFIED!");
2214  MACH3LOG_ERROR("You gave {}", static_cast<int>(Criterion));
2215  throw MaCh3Exception(__FILE__ , __LINE__ );
2216  }
2217  MACH3LOG_INFO("******************************");
2218 }
void StudyBIC()
Study Bayesian Information Criterion (BIC) .
void StudyDIC()
KS: Get the Deviance Information Criterion (DIC) .
void StudyWAIC()
KS: Get the Watanabe-Akaike information criterion (WAIC) .
@ kWAIC
Watanabe-Akaike information criterion.
@ kInfCrits
This only enumerates.
@ kBIC
Bayesian Information Criterion.
@ kDIC
Deviance Information Criterion.

◆ StudyKinematicCorrelations()

void SampleSummary::StudyKinematicCorrelations ( )
inlineprivate

KS: Study how correlated are sample or kinematic bins.

Definition at line 1685 of file SampleSummary.cpp.

1685  {
1686 // ****************
1687  MACH3LOG_INFO("Calculating Correlations");
1688  TStopwatch timer;
1689  timer.Start();
1690 
1691  // Data vs Draw for 1D projection
1692  std::vector<double> NEvents_Sample(nSamples);
1693  double event_rate = 0.;
1694 
1695  // The output tree we're going to write to
1696  TTree* Event_Rate_Tree = new TTree("Event_Rate_draws", "Event_Rate_draws");
1697  Event_Rate_Tree->Branch("Event_Rate", &event_rate);
1698  // Loop over the samples and set the addresses of the variables to write to file
1699  for (int i = 0; i < nSamples; ++i)
1700  {
1701  // Get the name
1702  std::string SampleName = SampleNames[i];
1703  //CW: Also strip out - signs because it messes up TBranches
1704  while (SampleName.find("-") != std::string::npos) {
1705  SampleName.replace(SampleName.find("-"), 1, std::string("_"));
1706  }
1707  Event_Rate_Tree->Branch((SampleName+"_Event_Rate").c_str(), &NEvents_Sample[i]);
1708  }
1709 
1710  // Holds the total event rate
1711  auto EventHist = std::make_unique<TH1D>("EventHist", "Total Event Rate", 100, 1, -1);
1712  EventHist->SetDirectory(nullptr);
1713  EventHist->GetXaxis()->SetTitle("Total event rate");
1714  EventHist->GetYaxis()->SetTitle("Counts");
1715  EventHist->SetLineWidth(2);
1716 
1717  // Holds the event rate for the distribution
1718  std::vector<std::unique_ptr<TH1D>> SumHist(nSamples);
1719  for (int i = 0; i < nSamples; ++i)
1720  {
1721  std::string name = std::string(NominalHist[i]->GetName());
1722  name = name.substr(0, name.find("_nom"));
1723 
1724  SumHist[i] = std::make_unique<TH1D>((name+"_sum").c_str(),(name+"_sum").c_str(), 100, 1, -1);
1725  SumHist[i]->GetXaxis()->SetTitle("N_{events}");
1726  SumHist[i]->GetYaxis()->SetTitle("Counts");
1727  double Integral = NoOverflowIntegral(DataHist[i]);
1728  std::stringstream ss;
1729  ss << Integral;
1730  SumHist[i]->SetTitle((std::string(SumHist[i]->GetTitle())+"_"+ss.str()).c_str());
1731  }
1732 
1733  for (unsigned int it = 0; it < nThrows; ++it)
1734  {
1735  double event_rate_temp = 0.;
1736  // Loop over the samples
1737  #ifdef MULTITHREAD
1738  #pragma omp parallel for reduction(+:event_rate_temp)
1739  #endif
1740  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
1741  {
1742  NEvents_Sample[SampleNum] = NoOverflowIntegral(MCVector[it][SampleNum]);
1743  // Fill the sum histogram with the integral of the sampled distribution
1744  SumHist[SampleNum]->Fill(NEvents_Sample[SampleNum], WeightVector[it]);
1745 
1746  event_rate_temp += NEvents_Sample[SampleNum];
1747  } // end samples loop
1748  event_rate = event_rate_temp;
1749  EventHist->Fill(event_rate);
1750  Event_Rate_Tree->Fill();
1751  } //end loops over throws
1752  Event_Rate_Tree->Write();
1753  delete Event_Rate_Tree;
1754 
1755  double DataRate = 0.0;
1756  #ifdef MULTITHREAD
1757  #pragma omp parallel for reduction(+:DataRate)
1758  #endif
1759  for (int i = 0; i < nSamples; ++i)
1760  {
1761  DataRate += NoOverflowIntegral(DataHist[i]);
1762  }
1763  MakeCutEventRate(EventHist.get(), DataRate);
1764 
1765  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
1766  {
1767  Dir[SampleNum]->cd();
1768  //Make fancy event rate histogram
1769  MakeCutEventRate(SumHist[SampleNum].get(), NoOverflowIntegral(DataHist[SampleNum]));
1770  }
1771 
1772  // Make a new directory
1773  TDirectory *CorrDir = Outputfile->mkdir("Correlations");
1774  CorrDir->cd();
1775 
1776  TMatrixDSym* SampleCorrelation = new TMatrixDSym(nSamples);
1777  std::vector<std::vector<std::unique_ptr<TH2D>>> SamCorr(nSamples);
1778  for (int i = 0; i < nSamples; ++i)
1779  {
1780  SamCorr[i].resize(nSamples);
1781 
1782  (*SampleCorrelation)(i,i) = 1.0;
1783  const double Min_i = SumHist[i]->GetXaxis()->GetBinLowEdge(1);
1784  const double Max_i = SumHist[i]->GetXaxis()->GetBinUpEdge(SumHist[i]->GetNbinsX()+1);
1785  for (int j = 0; j < nSamples; ++j)
1786  {
1787  const double Min_j = SumHist[j]->GetXaxis()->GetBinLowEdge(1);
1788  const double Max_j = SumHist[j]->GetXaxis()->GetBinUpEdge(SumHist[j]->GetNbinsX()+1);
1789 
1790  // TH2D to hold the Correlation
1791  SamCorr[i][j] = std::make_unique<TH2D>(Form("SamCorr_%i_%i", i, j), Form("SamCorr_%i_%i", i, j), 70, Min_i, Max_i, 70, Min_j, Max_j);
1792  SamCorr[i][j]->SetDirectory(nullptr);
1793  SamCorr[i][j]->SetMinimum(0);
1794  SamCorr[i][j]->GetXaxis()->SetTitle(SampleNames[i].c_str());
1795  SamCorr[i][j]->GetYaxis()->SetTitle(SampleNames[j].c_str());
1796  SamCorr[i][j]->GetZaxis()->SetTitle("Events");
1797  }
1798  }
1799 
1800  // Now we are sure we have the diagonal elements, let's make the off-diagonals
1801  #ifdef MULTITHREAD
1802  #pragma omp parallel for
1803  #endif
1804  for (int i = 0; i < nSamples; ++i)
1805  {
1806  for (int j = 0; j <= i; ++j)
1807  {
1808  // Skip the diagonal elements which we've already done above
1809  if (j == i) continue;
1810 
1811  for (unsigned int it = 0; it < nThrows; ++it)
1812  {
1813  SamCorr[i][j]->Fill(NoOverflowIntegral(MCVector[it][i]), NoOverflowIntegral(MCVector[it][j]));
1814  }
1815  SamCorr[i][j]->Smooth();
1816 
1817  // Get the Covariance for these two parameters
1818  (*SampleCorrelation)(i,j) = SamCorr[i][j]->GetCorrelationFactor();
1819  (*SampleCorrelation)(j,i) = (*SampleCorrelation)(i,j);
1820  }// End j loop
1821  }// End i loop
1822 
1823  auto hSamCorr = std::make_unique<TH2D>("Sample Correlation", "Sample Correlation", nSamples, 0, nSamples, nSamples, 0, nSamples);
1824  hSamCorr->SetDirectory(nullptr);
1825  hSamCorr->GetZaxis()->SetTitle("Correlation");
1826  hSamCorr->SetMinimum(-1);
1827  hSamCorr->SetMaximum(1);
1828  hSamCorr->GetXaxis()->SetLabelSize(0.015);
1829  hSamCorr->GetYaxis()->SetLabelSize(0.015);
1830 
1831  // Loop over the Covariance matrix entries
1832  for (int i = 0; i < nSamples; ++i)
1833  {
1834  hSamCorr->GetXaxis()->SetBinLabel(i+1, SampleNames[i].c_str());
1835 
1836  for (int j = 0; j < nSamples; ++j)
1837  {
1838  hSamCorr->GetYaxis()->SetBinLabel(j+1, SampleNames[j].c_str());
1839  // The value of the Covariance
1840  const double corr = (*SampleCorrelation)(i,j);
1841  hSamCorr->SetBinContent(i+1, j+1, corr);
1842  }
1843  }
1844  hSamCorr->Draw("colz");
1845  hSamCorr->Write("Sample_Corr");
1846 
1847  SampleCorrelation->Write("Sample_Correlation");
1848  delete SampleCorrelation;
1849 
1850  for (int i = 0; i < nSamples; ++i)
1851  {
1852  for (int j = 0; j <= i; ++j)
1853  {
1854  // Skip the diagonal elements which we've already done above
1855  if (j == i) continue;
1856  SamCorr[i][j]->Write();
1857  }// End j loop
1858  }// End i loop
1859 
1860  //KS: This can take ages so better turn it off by default
1861  bool DoPerKinemBin = false;
1862  if(DoPerKinemBin)
1863  {
1864  //KS: Now the same but for kinematic bin of each sample
1865  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
1866  {
1867  TMatrixDSym* KinCorrelation = new TMatrixDSym(maxBins[SampleNum]);
1868  std::vector<std::vector<std::unique_ptr<TH2D>>> KinCorr(maxBins[SampleNum]);
1869  for (int i = 0; i < maxBins[SampleNum]; ++i)
1870  {
1871  KinCorr[i].resize(maxBins[SampleNum]);
1872  (*KinCorrelation)(i,i) = 1.0;
1873 
1874  const double Min_i = PosteriorHist[SampleNum][i+1]->GetXaxis()->GetBinLowEdge(1);
1875  const double Max_i = PosteriorHist[SampleNum][i+1]->GetXaxis()->GetBinUpEdge(PosteriorHist[SampleNum][i+1]->GetNbinsX()+1);
1876 
1877  //Get PolyBin
1878  TH2PolyBin* bin = static_cast<TH2PolyBin*>(NominalHist[SampleNum]->GetBins()->At(i));
1879  // Just make a little fancy name
1880  std::stringstream ss2;
1881  ss2 << "p_{#mu} (" << bin->GetXMin() << "-" << bin->GetXMax() << ")";
1882  ss2 << " cos#theta_{#mu} (" << bin->GetYMin() << "-" << bin->GetYMax() << ")";
1883 
1884  for (int j = 0; j < maxBins[SampleNum]; ++j)
1885  {
1886  const double Min_j = PosteriorHist[SampleNum][j+1]->GetXaxis()->GetBinLowEdge(1);
1887  const double Max_j = PosteriorHist[SampleNum][j+1]->GetXaxis()->GetBinUpEdge(PosteriorHist[SampleNum][j+1]->GetNbinsX()+1);
1888 
1889  // TH2D to hold the Correlation
1890  KinCorr[i][j] = std::make_unique<TH2D>( Form("Kin_%i_%i_%i", SampleNum, i, j),
1891  Form("Kin_%i_%i_%i", SampleNum, i, j), 70, Min_i, Max_i, 70, Min_j, Max_j);
1892  KinCorr[i][j]->SetDirectory(nullptr);
1893  KinCorr[i][j]->SetMinimum(0);
1894 
1895  KinCorr[i][j]->GetXaxis()->SetTitle(ss2.str().c_str());
1896 
1897  bin = static_cast<TH2PolyBin*>(NominalHist[SampleNum]->GetBins()->At(j));
1898  // Just make a little fancy name
1899  std::stringstream ss3;
1900  ss3 << "p_{#mu} (" << bin->GetXMin() << "-" << bin->GetXMax() << ")";
1901  ss3 << " cos#theta_{#mu} (" << bin->GetYMin() << "-" << bin->GetYMax() << ")";
1902  KinCorr[i][j]->GetYaxis()->SetTitle(ss3.str().c_str());
1903  KinCorr[i][j]->GetZaxis()->SetTitle("Events");
1904  }
1905  }
1906  // Now we are sure we have the diagonal elements, let's make the off-diagonals
1907  #ifdef MULTITHREAD
1908  #pragma omp parallel for
1909  #endif
1910  for (int i = 0; i < maxBins[SampleNum]; ++i)
1911  {
1912  for (int j = 0; j <= i; ++j)
1913  {
1914  // Skip the diagonal elements which we've already done above
1915  if (j == i) continue;
1916 
1917  for (unsigned int it = 0; it < nThrows; ++it)
1918  {
1919  KinCorr[i][j]->Fill(MCVector[it][SampleNum]->GetBinContent(i+1), MCVector[it][SampleNum]->GetBinContent(j+1));
1920  }
1921  KinCorr[i][j]->Smooth();
1922 
1923  // Get the Covariance for these two parameters
1924  (*KinCorrelation)(i,j) = KinCorr[i][j]->GetCorrelationFactor();
1925  (*KinCorrelation)(j,i) = (*KinCorrelation)(i,j);
1926  }// End j loop
1927  }// End i loop
1928 
1929  auto hKinCorr = std::make_unique<TH2D>(SampleNames[SampleNum].c_str(), SampleNames[SampleNum].c_str(),
1930  maxBins[SampleNum], 0, maxBins[SampleNum], maxBins[SampleNum], 0, maxBins[SampleNum]);
1931  hKinCorr->SetDirectory(nullptr);
1932  hKinCorr->GetZaxis()->SetTitle("Correlation");
1933  hKinCorr->SetMinimum(-1);
1934  hKinCorr->SetMaximum(1);
1935  hKinCorr->GetXaxis()->SetLabelSize(0.015);
1936  hKinCorr->GetYaxis()->SetLabelSize(0.015);
1937 
1938  // Loop over the Covariance matrix entries
1939  for (int i = 0; i < maxBins[SampleNum]; ++i)
1940  {
1941  //Get PolyBin
1942  TH2PolyBin* bin = static_cast<TH2PolyBin*>(NominalHist[SampleNum]->GetBins()->At(i));
1943  // Just make a little fancy name
1944  std::stringstream ss2;
1945  ss2 << "p_{#mu} (" << bin->GetXMin() << "-" << bin->GetXMax() << ")";
1946  ss2 << " cos#theta_{#mu} (" << bin->GetYMin() << "-" << bin->GetYMax() << ")";
1947  hKinCorr->GetXaxis()->SetBinLabel(i+1, ss2.str().c_str());
1948 
1949  for (int j = 0; j < maxBins[SampleNum]; ++j)
1950  {
1951  bin = static_cast<TH2PolyBin*>(NominalHist[SampleNum]->GetBins()->At(j));
1952  // Just make a little fancy name
1953  std::stringstream ss3;
1954  ss3 << "p_{#mu} (" << bin->GetXMin() << "-" << bin->GetXMax() << ")";
1955  ss3 << " cos#theta_{#mu} (" << bin->GetYMin() << "-" << bin->GetYMax() << ")";
1956  KinCorr[i][j]->GetYaxis()->SetTitle(ss3.str().c_str());
1957 
1958  hKinCorr->GetYaxis()->SetBinLabel(j+1, ss3.str().c_str());
1959  // The value of the Covariance
1960  const double corr = (*KinCorrelation)(i,j);
1961  hKinCorr->SetBinContent(i+1, j+1, corr);
1962  }
1963  }
1964  hKinCorr->Draw("colz");
1965  hKinCorr->Write((SampleNames[SampleNum] + "_Corr").c_str());
1966 
1967  KinCorrelation->Write((SampleNames[SampleNum] + "_Correlation").c_str());
1968  delete KinCorrelation;
1969 
1970  /*
1971  for (int i = 0; i < maxBins[SampleNum]; ++i)
1972  {
1973  for (int j = 0; j <= i; ++j)
1974  {
1975  // Skip the diagonal elements which we've already done above
1976  if (j == i) continue;
1977  KinCorr[i][j]->Write();
1978  }// End j loop
1979  }// End i loop
1980  */
1981  }//end loop over samples
1982  }//end if DoPerKinemBin
1983  else
1984  {
1985  MACH3LOG_INFO("Not calculating correlations per each kinematic bin");
1986  }
1987 
1988  if(DoByModePlots)
1989  {
1990  // Holds the total event rate by mode
1991  std::vector<TH1D*> EventHist_ByMode(Modes->GetNModes()+1);
1992  for (int j = 0; j < Modes->GetNModes()+1; j++)
1993  {
1994  std::string ModeName = Modes->GetMaCh3ModeName(j);
1995  EventHist_ByMode[j] = new TH1D(Form("EventHist_%s", ModeName.c_str()), Form("Total Event Rate %s", ModeName.c_str()), 100, 1, -1);
1996  EventHist_ByMode[j]->GetXaxis()->SetTitle("Total event rate");
1997  EventHist_ByMode[j]->GetYaxis()->SetTitle("Counts");
1998  EventHist_ByMode[j]->SetLineWidth(2);
1999  }
2000 
2001  //KS: Here we calculate total event rates for each mode, maybe not most efficient but can be improved in the future
2002  for (unsigned int it = 0; it < nThrows; ++it)
2003  {
2004  for (int j = 0; j < Modes->GetNModes()+1; j++)
2005  {
2006  double event_rate_temp = 0.;
2007  #ifdef MULTITHREAD
2008  #pragma omp parallel for reduction(+:event_rate_temp)
2009  #endif
2010  for (int SampleNum = 0; SampleNum < nSamples; SampleNum++)
2011  {
2012  event_rate_temp += NoOverflowIntegral(MCVectorByMode[it][SampleNum][j]);
2013  }
2014  EventHist_ByMode[j]->Fill(event_rate_temp);
2015  }
2016  }
2017 
2018  for (int i = 0; i < Modes->GetNModes()+1; ++i)
2019  {
2020  MakeCutEventRate(EventHist_ByMode[i], DataRate);
2021  }
2022 
2023  TMatrixDSym* ModeCorrelation = new TMatrixDSym(Modes->GetNModes()+1);
2024 
2025  TH2D*** ModeCorr = new TH2D**[Modes->GetNModes()+1]();
2026  for (int i = 0; i < Modes->GetNModes()+1; ++i)
2027  {
2028  ModeCorr[i] = new TH2D*[Modes->GetNModes()+1]();
2029 
2030  (*ModeCorrelation)(i,i) = 1.0;
2031 
2032  const double Min_i = EventHist_ByMode[i]->GetXaxis()->GetBinLowEdge(1);
2033  const double Max_i = EventHist_ByMode[i]->GetXaxis()->GetBinUpEdge(EventHist_ByMode[i]->GetNbinsX()+1);
2034  for (int j = 0; j < Modes->GetNModes()+1; ++j)
2035  {
2036  const double Min_j = EventHist_ByMode[j]->GetXaxis()->GetBinLowEdge(1);
2037  const double Max_j = EventHist_ByMode[j]->GetXaxis()->GetBinUpEdge(EventHist_ByMode[j]->GetNbinsX()+1);
2038 
2039  // TH2D to hold the Correlation
2040  ModeCorr[i][j] = new TH2D(Form("ModeCorr_%i_%i",i,j), Form("ModeCorr_%i_%i",i,j), 70, Min_i, Max_i, 70, Min_j, Max_j);
2041  ModeCorr[i][j]->SetDirectory(nullptr);
2042  ModeCorr[i][j]->SetMinimum(0);
2043  ModeCorr[i][j]->GetXaxis()->SetTitle(Modes->GetMaCh3ModeName(i).c_str());
2044  ModeCorr[i][j]->GetYaxis()->SetTitle(Modes->GetMaCh3ModeName(j).c_str());
2045  ModeCorr[i][j]->GetZaxis()->SetTitle("Events");
2046  }
2047  }
2048 
2049  // Now we are sure we have the diagonal elements, let's make the off-diagonals
2050  #ifdef MULTITHREAD
2051  #pragma omp parallel for
2052  #endif
2053  for (int i = 0; i < Modes->GetNModes()+1; ++i)
2054  {
2055  for (int j = 0; j <= i; ++j)
2056  {
2057  // Skip the diagonal elements which we've already done above
2058  if (j == i) continue;
2059 
2060  for (unsigned int it = 0; it < nThrows; ++it)
2061  {
2062  double Integral_X = 0.;
2063  double Integral_Y = 0.;
2064  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum)
2065  {
2066  Integral_X += NoOverflowIntegral(MCVectorByMode[it][SampleNum][i]);
2067  Integral_Y += NoOverflowIntegral(MCVectorByMode[it][SampleNum][j]);
2068  }
2069  ModeCorr[i][j]->Fill(Integral_X, Integral_Y);
2070  }
2071  ModeCorr[i][j]->Smooth();
2072 
2073  // Get the Covariance for these two parameters
2074  (*ModeCorrelation)(i,j) = ModeCorr[i][j]->GetCorrelationFactor();
2075  (*ModeCorrelation)(j,i) = (*ModeCorrelation)(i,j);
2076  }// End j loop
2077  }// End i loop
2078 
2079  TH2D* hModeCorr = new TH2D("Mode Correlation", "Mode Correlation", Modes->GetNModes()+1, 0, Modes->GetNModes()+1, Modes->GetNModes()+1, 0, Modes->GetNModes()+1);
2080  hModeCorr->SetDirectory(nullptr);
2081  hModeCorr->GetZaxis()->SetTitle("Correlation");
2082  hModeCorr->SetMinimum(-1);
2083  hModeCorr->SetMaximum(1);
2084  hModeCorr->GetXaxis()->SetLabelSize(0.015);
2085  hModeCorr->GetYaxis()->SetLabelSize(0.015);
2086 
2087  // Loop over the Covariance matrix entries
2088  for (int i = 0; i < Modes->GetNModes()+1; ++i)
2089  {
2090  hModeCorr->GetXaxis()->SetBinLabel(i+1, Modes->GetMaCh3ModeName(i).c_str());
2091 
2092  for (int j = 0; j < Modes->GetNModes()+1; ++j)
2093  {
2094  hModeCorr->GetYaxis()->SetBinLabel(j+1, Modes->GetMaCh3ModeName(j).c_str());
2095  // The value of the Covariance
2096  const double corr = (*ModeCorrelation)(i,j);
2097  hModeCorr->SetBinContent(i+1, j+1, corr);
2098  }
2099  }
2100  hModeCorr->Draw("colz");
2101  hModeCorr->Write("Mode_Corr");
2102  delete hModeCorr;
2103 
2104  for (int i = 0; i < Modes->GetNModes()+1; ++i)
2105  {
2106  for (int j = 0; j <= i; ++j)
2107  {
2108  // Skip the diagonal elements which we've already done above
2109  if (j == i) continue;
2110  ModeCorr[i][j]->Write();
2111  }// End j loop
2112  }// End i loop
2113 
2114  for (int i = 0; i < Modes->GetNModes()+1; ++i)
2115  {
2116  for (int j = 0; j < Modes->GetNModes()+1; ++j)
2117  {
2118  delete ModeCorr[i][j];
2119  }
2120  delete[] ModeCorr[i];
2121  }
2122  delete[] ModeCorr;
2123  ModeCorrelation->Write("Mode_Correlation");
2124  delete ModeCorrelation;
2125 
2126  for (int j = 0; j < Modes->GetNModes()+1; j++)
2127  {
2128  delete EventHist_ByMode[j];
2129  }
2130  }
2131 
2132  CorrDir->Close();
2133  delete CorrDir;
2134 
2135  timer.Stop();
2136  MACH3LOG_INFO("Calculating correlations took {:.2f}s", timer.RealTime());
2137  Outputfile->cd();
2138 }
void MakeCutEventRate(TH1D *Histogram, const double DataRate)
Make the 1D Event Rate Hist.

◆ StudyWAIC()

void SampleSummary::StudyWAIC ( )
inlineprivate

KS: Get the Watanabe-Akaike information criterion (WAIC) [13] [18].

Definition at line 2279 of file SampleSummary.cpp.

2279  {
2280 // ****************
2281  // log pointwise predictive density
2282  double lppd = 0.;
2283  // effective number of parameters
2284  double p_WAIC = 0.;
2285 
2286  #ifdef MULTITHREAD
2287  #pragma omp parallel for reduction(+:lppd, p_WAIC)
2288  #endif
2289  for (int SampleNum = 0; SampleNum < nSamples; ++SampleNum) {
2290  int nBins = maxBins[SampleNum];
2291  for (int i = 1; i <= nBins; ++i) {
2292  double mean_llh = 0.;
2293  double sum_exp_llh = 0;
2294  double mean_llh_squared = 0.;
2295 
2296  for (unsigned int s = 0; s < nThrows; ++s) {
2297  const double data = DataHist[SampleNum]->GetBinContent(i);
2298  const double mc = MCVector[s][SampleNum]->GetBinContent(i);
2299  const double w2 = W2MCVector[s][SampleNum]->GetBinContent(i);
2300 
2301  // Get the -log-likelihood for this sample and bin
2302  double neg_LLH_temp = SampleHandler->GetTestStatLLH(data, mc, w2);
2303 
2304  // Negate the negative log-likelihood to get the actual log-likelihood
2305  double LLH_temp = -neg_LLH_temp;
2306 
2307  mean_llh += LLH_temp;
2308  mean_llh_squared += LLH_temp * LLH_temp;
2309  sum_exp_llh += std::exp(LLH_temp);
2310  }
2311 
2312  // Compute the mean log-likelihood and the squared mean
2313  mean_llh /= nThrows;
2314  mean_llh_squared /= nThrows;
2315  sum_exp_llh /= nThrows;
2316  sum_exp_llh = std::log(sum_exp_llh);
2317 
2318  // Log pointwise predictive density based on Eq. 4 in Gelman2014
2319  lppd += sum_exp_llh;
2320 
2321  // Compute the effective number of parameters for WAIC
2322  p_WAIC += mean_llh_squared - (mean_llh * mean_llh);
2323  }
2324  }
2325 
2326  // Compute WAIC, see Eq. 13 in Gelman2014
2327  double WAIC = -2 * (lppd - p_WAIC);
2328  MACH3LOG_INFO("Effective number of parameters following WAIC formalism is equal to: {:.2f}", p_WAIC);
2329  MACH3LOG_INFO("WAIC = {:.2f}", WAIC);
2330 }

◆ Write()

void SampleSummary::Write ( )

KS: Write results into root file.

Definition at line 666 of file SampleSummary.cpp.

666  {
667 // *******************
668  // Prepare the output tree
669  PrepareOutput();
670 
671  MACH3LOG_INFO("Summarising {} throws...", nThrows);
672  // After all the throws are added finalise the sample
673  TStopwatch timer;
674  timer.Start();
675  MakePredictive();
676  timer.Stop();
677  MACH3LOG_INFO("Made Prior/Posterior Predictive, it took {:.2f}s, now writing...", timer.RealTime());
678 
679  // Studying information criterion
681 
682  OutputTree->Write();
683 
684  // Make the various distributions
685  lnLHist->Write();
686  lnLHist_drawfluc->Write();
687  lnLHist_drawflucdraw->Write();
688  lnLHist_drawdata->Write();
689  lnLDrawHist->Write();
690  lnLFlucHist->Write();
691  lnLDrawHistRate->Write();
692  //KS: Only available for Posterior Predictive
693  if(!isPriorPredictive) RandomHist->Write();
694 
695  lnLFlucHist_ProjectX->Write();
696 
697  // Loop over each sample and write to file
698  //KS: Multithreading is tempting here but we also write to ROOT file, separating all LLH and poly projections from write could work well
699  for (int i = 0; i < nSamples; ++i)
700  {
701  // Skip the null histograms
702  if (DataHist[i] == nullptr || NoOverflowIntegral(DataHist[i]) == 0) continue;
703  Dir[i]->cd();
704 
705  // Make the data/MC ratio histogram
706  TH2Poly *RatioHistMean = RatioPolys(DataHist[i], MeanHist[i]);
707  RatioHistMean->GetZaxis()->SetTitle("Data/Mean");
708  TH2Poly *RatioHistMode = RatioPolys(DataHist[i], ModeHist[i]);
709  RatioHistMode->GetZaxis()->SetTitle("Data/Mode");
710  TH2Poly *RatioHistNom = RatioPolys(DataHist[i], NominalHist[i]);
711  RatioHistNom->GetZaxis()->SetTitle("Data/Nom");
712 
713  // And the normalised data histogram
714  TH2Poly *DataNormHist = NormalisePoly(DataHist[i]);
715  // Last true refers to if project along x or y
716  TH2Poly *MeanNormHist = NormalisePoly(MeanHist[i]);
717  TH2Poly *ModeNormHist = NormalisePoly(ModeHist[i]);
718  TH1D *MeanProjectX = ProjectPoly(MeanHist[i], true, i, true);
719  TH1D *MeanProjectY = ProjectPoly(MeanHist[i], false, i, true);
720  TH1D *ModeProjectX = ProjectPoly(ModeHist[i], true, i, true);
721  TH1D *ModeProjectY = ProjectPoly(ModeHist[i], false, i, true);
722 
723  TH1D *MeanHistCorrectedProjectX = nullptr;
724  if(DoBetaParam) MeanHistCorrectedProjectX = ProjectPoly(MeanHistCorrected[i], true, i, true);
725  TH1D *MeanHistCorrectedProjectY = nullptr;
726  if(DoBetaParam) MeanHistCorrectedProjectY = ProjectPoly(MeanHistCorrected[i], false, i, true);
727 
728  TH1D *W2MeanProjectX = ProjectPoly(W2MeanHist[i], true, i);
729  TH1D *W2MeanProjectY = ProjectPoly(W2MeanHist[i], false, i);
730  TH1D *W2ModeProjectX = ProjectPoly(W2ModeHist[i], true, i);
731  TH1D *W2ModeProjectY = ProjectPoly(W2ModeHist[i], false, i);
732 
733  TH2Poly *NomNormHist = NormalisePoly(NominalHist[i]);
734  TH1D *NomProjectX = ProjectPoly(NominalHist[i], true, i);
735  TH1D *NomProjectY = ProjectPoly(NominalHist[i], false, i);
736 
737  TH1D *W2NomProjectX = ProjectPoly(W2NomHist[i], true, i);
738  TH1D *W2NomProjectY = ProjectPoly(W2NomHist[i], false, i);
739 
740  // Same for the TH2Ds
742  CalcLLH(DataHist[i], MeanHist[i], W2MeanHist[i]);
743  CalcLLH(DataHist[i], ModeHist[i], W2ModeHist[i]);
744 
745  // Calculate the log likelihood for the 1D dists
746  // Sets the title of the second TH1D to the -2LLH
747  CalcLLH(DataHist_ProjectX[i], NomProjectX, W2NomProjectX);
748  CalcLLH(DataHist_ProjectX[i], MeanProjectX, W2MeanProjectX);
749  CalcLLH(DataHist_ProjectX[i], ModeProjectX, W2ModeProjectX);
750  CalcLLH(DataHist_ProjectY[i], NomProjectY, W2NomProjectY);
751  CalcLLH(DataHist_ProjectY[i], MeanProjectY, W2MeanProjectY);
752  CalcLLH(DataHist_ProjectY[i], ModeProjectY, W2ModeProjectY);
753 
754  std::string SampleName = SampleNames[i];
755  // Also strip out - signs because it messes up TBranches
756  while (SampleName.find("-") != std::string::npos) {
757  SampleName.replace(SampleName.find("-"), 1, std::string("_"));
758  }
759  OutputTree->Draw((SampleName+"_data_draw:"+SampleName+"_drawfluc_draw>>htemp").c_str());
760  TH2D *TempHistogram = static_cast<TH2D*>(gDirectory->Get("htemp")->Clone());
761  TempHistogram->GetXaxis()->SetTitle("-2LLH(Draw Fluc, Draw)");
762  TempHistogram->GetYaxis()->SetTitle("-2LLH(Data, Draw)");
763  TempHistogram->SetNameTitle((SampleNames[i]+"_drawfluc_draw").c_str(), (SampleNames[i]+"_drawfluc_draw").c_str());
764  Get2DBayesianpValue(TempHistogram);
765  TempHistogram->Write();
766  delete TempHistogram;
767 
768  // Also write the 2D histograms for the p-value
769  OutputTree->Draw((SampleName+"_data_draw:"+SampleName+"_predfluc_draw>>htemp2").c_str());
770  TH2D *TempHistogram2 = static_cast<TH2D*>(gDirectory->Get("htemp2")->Clone());
771  TempHistogram2->GetXaxis()->SetTitle("-2LLH(Pred Fluc, Draw)");
772  TempHistogram2->GetYaxis()->SetTitle("-2LLH(Data, Draw)");
773  TempHistogram2->SetNameTitle((SampleNames[i]+"_predfluc_draw").c_str(), (SampleNames[i]+"_predfluc_draw").c_str());
774  Get2DBayesianpValue(TempHistogram2);
775  TempHistogram2->Write();
776  delete TempHistogram2;
777 
778  // finally p-value for 1D projection
779  OutputTree->Draw((SampleName+"_rate_data_draw:"+SampleName+"_rate_predfluc_draw>>htemp3").c_str());
780  TH2D *TempHistogram3 = static_cast<TH2D*>(gDirectory->Get("htemp3")->Clone());
781  TempHistogram3->GetXaxis()->SetTitle("-2LLH(Pred Fluc, Draw)");
782  TempHistogram3->GetYaxis()->SetTitle("-2LLH(Data, Draw)");
783  TempHistogram3->SetNameTitle((SampleNames[i]+"_rate_predfluc_draw").c_str(), (SampleNames[i]+"_rate_predfluc_draw").c_str());
784  Get2DBayesianpValue(TempHistogram3);
785  TempHistogram3->Write();
786  delete TempHistogram3;
787 
788  // finally p-value for 1D projection
789  OutputTree->Draw((SampleName+"_data_draw_ProjectX:"+SampleName+"_drawfluc_draw_ProjectX>>htemp4").c_str());
790  TH2D *TempHistogram4 = static_cast<TH2D*>(gDirectory->Get("htemp4")->Clone());
791  TempHistogram4->GetXaxis()->SetTitle(("-2LLH_{Draw Fluc, Draw} for " + SampleHandler->GetKinVarName(i, 0)).c_str());
792  TempHistogram4->GetYaxis()->SetTitle(("-2LLH_{Data, Draw} for " + SampleHandler->GetKinVarName(i, 0)).c_str());
793  TempHistogram4->SetNameTitle((SampleNames[i]+"_drawfluc_draw_ProjectX").c_str(), (SampleNames[i]+"_drawfluc_draw_ProjectX").c_str());
794  Get2DBayesianpValue(TempHistogram4);
795  TempHistogram4->Write();
796  delete TempHistogram4;
797 
798  // Write the Histograms to each folder
799  DataHist[i]->Write();
800  NominalHist[i]->Write();
801  MeanHist[i]->Write();
802  ModeHist[i]->Write();
803  RatioHistMean->Write();
804  RatioHistMode->Write();
805  RatioHistNom->Write();
806  if(DoBetaParam) MeanHistCorrected[i]->Write();
807 
808  W2NomHist[i]->Write();
809  W2MeanHist[i]->Write();
810  W2ModeHist[i]->Write();
811 
812  DataNormHist->Write();
813  NomNormHist->Write();
814  MeanNormHist->Write();
815  ModeNormHist->Write();
816 
817  DataHist_ProjectX[i]->Write();
818  NomProjectX->Write();
819  MeanProjectX->Write();
820  ModeProjectX->Write();
821  if(DoBetaParam) MeanHistCorrectedProjectX->Write();
822  ViolinHists_ProjectX[i]->Write();
823 
824  DataHist_ProjectY[i]->Write();
825  NomProjectY->Write();
826  MeanProjectY->Write();
827  ModeProjectY->Write();
828  if(DoBetaParam) MeanHistCorrectedProjectY->Write();
829  ViolinHists_ProjectY[i]->Write();
830 
831  W2NomProjectX->Write();
832  W2MeanProjectX->Write();
833  W2ModeProjectX->Write();
834 
835  W2NomProjectY->Write();
836  W2MeanProjectY->Write();
837  W2ModeProjectY->Write();
838 
839  //KS: This will dump lots of hists, use it only for debugging
840  if(Debug > 0)
841  {
842  TDirectory* DebugDir = Dir[i]->mkdir("Debug");
843  DebugDir->cd();
844  for (int b = 1; b <= maxBins[i]; ++b)
845  {
846  PosteriorHist[i][b]->Write();
847  std::string Title = PosteriorHist[i][b]->GetName();
848 
849  auto TempLine = std::make_unique<TLine>(NominalHist[i]->GetBinContent(b), PosteriorHist[i][b]->GetMinimum(),
850  NominalHist[i]->GetBinContent(b), PosteriorHist[i][b]->GetMaximum());
851  TempLine->SetLineColor(kRed);
852  TempLine->SetLineWidth(2);
853 
854  auto TempLineData = std::make_unique<TLine>(DataHist[i]->GetBinContent(b), PosteriorHist[i][b]->GetMinimum(),
855  DataHist[i]->GetBinContent(b), PosteriorHist[i][b]->GetMaximum());
856  TempLineData->SetLineColor(kGreen);
857  TempLineData->SetLineWidth(2);
858 
859  // Also fit a Gaussian because why not?
860  TF1 *Fitter = new TF1("Fit", "gaus", PosteriorHist[i][b]->GetBinLowEdge(1), PosteriorHist[i][b]->GetBinLowEdge(PosteriorHist[i][b]->GetNbinsX()+1));
861  PosteriorHist[i][b]->Fit(Fitter, "RQ");
862  Fitter->SetLineColor(kRed-5);
863 
864  auto Legend = std::make_unique<TLegend>(0.4, 0.75, 0.98, 0.90);
865  Legend->SetFillColor(0);
866  Legend->SetFillStyle(0);
867  Legend->SetLineWidth(0);
868  Legend->SetLineColor(0);
869  Legend->AddEntry(TempLineData.get(), Form("Data #mu=%.2f", DataHist[i]->GetBinContent(b)), "l");
870  Legend->AddEntry(TempLine.get(), Form("Prior #mu=%.2f", NominalHist[i]->GetBinContent(b)), "l");
871  Legend->AddEntry(PosteriorHist[i][b].get(), Form("Post, #mu=%.2f#pm%.2f", PosteriorHist[i][b]->GetMean(), PosteriorHist[i][b]->GetRMS()), "l");
872  Legend->AddEntry(Fitter, Form("Gauss, #mu=%.2f#pm%.2f", Fitter->GetParameter(1), Fitter->GetParameter(2)), "l");
873  std::string TempTitle = std::string(PosteriorHist[i][b]->GetName());
874 
875  TempTitle += "_canv";
876  TCanvas *TempCanvas = new TCanvas(TempTitle.c_str(), TempTitle.c_str(), 1024, 1024);
877  TempCanvas->SetGridx();
878  TempCanvas->SetGridy();
879  TempCanvas->SetRightMargin(0.03);
880  TempCanvas->SetBottomMargin(0.08);
881  TempCanvas->SetLeftMargin(0.10);
882  TempCanvas->SetTopMargin(0.06);
883  TempCanvas->cd();
884  PosteriorHist[i][b]->Draw();
885  TempLine->Draw("same");
886  TempLineData->Draw("same");
887  Fitter->Draw("same");
888  Legend->Draw("same");
889  TempCanvas->Write();
890 
891  delete TempCanvas;
892  delete Fitter;
893  //This isn't useful check only in desperation
894  if(Debug > 1) w2Hist[i][b]->Write();
895  }
896  DebugDir->Close();
897  delete DebugDir;
898  Dir[i]->cd();
899  }
900  lnLHist_Mean[i]->Write();
901  lnLHist_Mode[i]->Write();
902 
903  lnLHist_Mean_ProjectX[i]->Write();
904 
905  lnLHist_Mean1D[i]->Write();
906  lnLHist_Mode1D[i]->Write();
907 
909  lnLHist_Sample_DrawData[i]->Write();
911  lnLHist_Sample_DrawflucDraw[i]->Write();
913  lnLHist_Sample_PredflucDraw[i]->Write();
914 
915  if(DoByModePlots)
916  {
917  for (int j = 0; j < Modes->GetNModes()+1; ++j)
918  {
919  MeanHist_ByMode[i][j]->Write();
920  TH1D *MeanProjectX_ByMode = ProjectPoly(MeanHist_ByMode[i][j], true, i, true);
921  TH1D *MeanProjectY_ByMode = ProjectPoly(MeanHist_ByMode[i][j], false, i, true);
922  MeanProjectX_ByMode->Write();
923  MeanProjectY_ByMode->Write();
924  //KS: This will dump lots of hists, use it only for debugging
925  if(Debug > 0)
926  {
927  for (int b = 1; b <= maxBins[i]; ++b)
928  {
929  PosteriorHist_ByMode[i][j][b]->Write();
930  }
931  }
932  delete MeanProjectX_ByMode;
933  delete MeanProjectY_ByMode;
934  } // End loop over bins
935  }
936  // Delete temporary objects
937  delete RatioHistMean;
938  delete RatioHistMode;
939  delete RatioHistNom;
940 
941  delete DataNormHist;
942  delete MeanNormHist;
943  delete ModeNormHist;
944  delete NomNormHist;
945 
946  delete DataHist_ProjectX[i];
947  delete MeanProjectX;
948  delete ModeProjectX;
949  if(DoBetaParam) delete MeanHistCorrectedProjectX;
950  delete NomProjectX;
951 
952  delete DataHist_ProjectY[i];
953  delete MeanProjectY;
954  delete ModeProjectY;
955  if(DoBetaParam) delete MeanHistCorrectedProjectY;
956  delete NomProjectY;
957 
958  delete W2NomProjectX;
959  delete W2MeanProjectX;
960  delete W2ModeProjectX;
961 
962  delete W2NomProjectY;
963  delete W2MeanProjectY;
964  delete W2ModeProjectY;
965  MACH3LOG_INFO("");
966  } //end loop over samples
968 
970  MACH3LOG_INFO("Wrote to {}", Outputfile->GetName());
971 }
TH2Poly * NormalisePoly(TH2Poly *Histogram)
WP: Helper to Normalise histograms.
TH2Poly * RatioPolys(TH2Poly *NumHist, TH2Poly *DenomHist)
Helper to make ratio of TH2Polys.
void StudyInformationCriterion(M3::kInfCrit Criterion)
Information Criterion.
void CalcLLH(TH2Poly *const &Data, TH2Poly *const &MC, TH2Poly *const &W2)
Helper functions to calculate likelihoods using TH2Poly, will modify MC hist title to include LLH.
void MakePredictive()
Finalise the distributions from the thrown samples.
void PrepareOutput()
KS: Prepare output tree and necessary variables.
void PlotBetaParameters()
KS: In Barlow Beeston we have Beta Parameters which scale generated MC.
void StudyKinematicCorrelations()
KS: Study how correlated are sample or kinematic bins.

Member Data Documentation

◆ BetaHist

std::vector<std::vector<std::unique_ptr<TH1D> > > SampleSummary::BetaHist
private

Distribution of beta parameters in Barlow Beeston formalisms.

Definition at line 222 of file SampleSummary.h.

◆ DataHist

std::vector<TH2Poly*> SampleSummary::DataHist
private

The data histogram for the selection.

Definition at line 159 of file SampleSummary.h.

◆ DataHist_ProjectX

std::vector<TH1D*> SampleSummary::DataHist_ProjectX
private

The data histogram for the selection X projection.

Definition at line 161 of file SampleSummary.h.

◆ DataHist_ProjectY

std::vector<TH1D*> SampleSummary::DataHist_ProjectY
private

The data histogram for the selection Y projection.

Definition at line 163 of file SampleSummary.h.

◆ Debug

int SampleSummary::Debug
private

Tells Debug level to save additional histograms.

Definition at line 340 of file SampleSummary.h.

◆ Dir

std::vector<TDirectory*> SampleSummary::Dir
private

Directory for each sample.

Definition at line 249 of file SampleSummary.h.

◆ DoBetaParam

bool SampleSummary::DoBetaParam
private

Are we making Beta Histograms.

Definition at line 224 of file SampleSummary.h.

◆ DoByModePlots

bool SampleSummary::DoByModePlots
private

By mode variables.

Definition at line 321 of file SampleSummary.h.

◆ doShapeOnly

bool SampleSummary::doShapeOnly
private

bool whether to normalise each toy to have shape based p-value and pos pred distribution

Definition at line 233 of file SampleSummary.h.

◆ first_pass

bool SampleSummary::first_pass
private

KS: Hacky flag to let us know if this is first toy.

Definition at line 125 of file SampleSummary.h.

◆ isPriorPredictive

bool SampleSummary::isPriorPredictive
private

bool whether we have Prior or Posterior Predictive

Definition at line 230 of file SampleSummary.h.

◆ likelihood

TestStatistic SampleSummary::likelihood
private

Type of likelihood for example Poisson, Barlow-Beeston or Ice Cube.

Definition at line 334 of file SampleSummary.h.

◆ llh_data_draw

std::vector<double> SampleSummary::llh_data_draw
private

Data vs Draw.

Definition at line 254 of file SampleSummary.h.

◆ llh_data_draw_ProjectX

std::vector<double> SampleSummary::llh_data_draw_ProjectX
private

Projection X (most likely muon momentum) of LLH.

Definition at line 282 of file SampleSummary.h.

◆ llh_data_drawfluc

std::vector<double> SampleSummary::llh_data_drawfluc
private

Data vs Fluctuated Draw.

Definition at line 266 of file SampleSummary.h.

◆ llh_data_predfluc

std::vector<double> SampleSummary::llh_data_predfluc
private

Data vs Fluctuated Predictive.

Definition at line 268 of file SampleSummary.h.

◆ llh_datafluc_draw

std::vector<double> SampleSummary::llh_datafluc_draw
private

Fluctuated Data vs Draw.

Definition at line 279 of file SampleSummary.h.

◆ llh_draw_pred

std::vector<double> SampleSummary::llh_draw_pred
private

Draw vs Predictive.

Definition at line 270 of file SampleSummary.h.

◆ llh_drawfluc_draw

std::vector<double> SampleSummary::llh_drawfluc_draw
private

Fluctuated Draw vs Draw.

Definition at line 256 of file SampleSummary.h.

◆ llh_drawfluc_draw_ProjectX

std::vector<double> SampleSummary::llh_drawfluc_draw_ProjectX
private

Definition at line 283 of file SampleSummary.h.

◆ llh_drawfluc_pred

std::vector<double> SampleSummary::llh_drawfluc_pred
private

Fluctuated Draw vs Predictive.

Definition at line 272 of file SampleSummary.h.

◆ llh_drawfluc_predfluc

std::vector<double> SampleSummary::llh_drawfluc_predfluc
private

Fluctuated Draw vs Fluctuated Predictive.

Definition at line 277 of file SampleSummary.h.

◆ llh_penalty

double SampleSummary::llh_penalty
private

LLH penalty for each throw.

Definition at line 286 of file SampleSummary.h.

◆ llh_predfluc_draw

std::vector<double> SampleSummary::llh_predfluc_draw
private

Fluctuated Predictive vs Draw.

Definition at line 258 of file SampleSummary.h.

◆ llh_predfluc_pred

std::vector<double> SampleSummary::llh_predfluc_pred
private

Fluctuated Predictive vs Predictive.

Definition at line 275 of file SampleSummary.h.

◆ llh_rate_data_draw

std::vector<double> SampleSummary::llh_rate_data_draw
private

Data vs Draw using rate only.

Definition at line 261 of file SampleSummary.h.

◆ llh_rate_predfluc_draw

std::vector<double> SampleSummary::llh_rate_predfluc_draw
private

Fluctuated Predictive vs Draw using rate only.

Definition at line 263 of file SampleSummary.h.

◆ llh_total

double SampleSummary::llh_total
private

Total LLH for the posterior predictive distribution.

Definition at line 242 of file SampleSummary.h.

◆ LLHPenaltyVector

std::vector<double> SampleSummary::LLHPenaltyVector
private

Vector to hold the penalty term.

Definition at line 138 of file SampleSummary.h.

◆ lnLDrawHist

std::unique_ptr<TH2D> SampleSummary::lnLDrawHist
private

The 2D lnLhist, showing (draw vs data) and (draw vs fluct), anything above y=x axis is the p-value.

Definition at line 182 of file SampleSummary.h.

◆ lnLDrawHistRate

std::unique_ptr<TH2D> SampleSummary::lnLDrawHistRate
private

The 2D lnLhist, showing (draw vs data) and (draw vs fluct), using rate, anything above y=x axis is the p-value.

Definition at line 187 of file SampleSummary.h.

◆ lnLFlucHist

std::unique_ptr<TH2D> SampleSummary::lnLFlucHist
private

The 2D lnLHist, showing (draw vs data) and (draw vs draw fluct), anything above y=x axis is the p-value.

Definition at line 184 of file SampleSummary.h.

◆ lnLFlucHist_ProjectX

std::unique_ptr<TH2D> SampleSummary::lnLFlucHist_ProjectX
private

The 2D lnLHist but for ProjectionX histogram (pmu), showing (draw vs data) and (draw vs draw fluct), anything above y=x axis is the p-value.

Definition at line 189 of file SampleSummary.h.

◆ lnLHist

std::unique_ptr<TH1D> SampleSummary::lnLHist
private

The histogram containing the lnL for each throw.

Definition at line 174 of file SampleSummary.h.

◆ lnLHist_drawdata

std::unique_ptr<TH1D> SampleSummary::lnLHist_drawdata
private

The lnLhist for the draw vs data.

Definition at line 180 of file SampleSummary.h.

◆ lnLHist_drawfluc

std::unique_ptr<TH1D> SampleSummary::lnLHist_drawfluc
private

The lnLhist for the draw vs MC fluctuated.

Definition at line 176 of file SampleSummary.h.

◆ lnLHist_drawflucdraw

std::unique_ptr<TH1D> SampleSummary::lnLHist_drawflucdraw
private

The lnLhist for the draw vs draw fluctuated.

Definition at line 178 of file SampleSummary.h.

◆ lnLHist_Mean

std::vector<TH2Poly*> SampleSummary::lnLHist_Mean
private

The LLH distribution in pmu cosmu for using the mean in each bin.

Definition at line 199 of file SampleSummary.h.

◆ lnLHist_Mean1D

std::vector<TH1D*> SampleSummary::lnLHist_Mean1D
private

Holds the bin-by-bin LLH for the mean posterior predictive vs the data.

Definition at line 214 of file SampleSummary.h.

◆ lnLHist_Mean_ProjectX

std::vector<TH1D*> SampleSummary::lnLHist_Mean_ProjectX
private

The LLH distribution in pmu using the mean in each bin.

Definition at line 204 of file SampleSummary.h.

◆ lnLHist_Mode

std::vector<TH2Poly*> SampleSummary::lnLHist_Mode
private

The LLH distribution in pmu cosmu for using the mode in each bin.

Definition at line 201 of file SampleSummary.h.

◆ lnLHist_Mode1D

std::vector<TH1D*> SampleSummary::lnLHist_Mode1D
private

Holds the bin-by-bin LLH for the mode posterior predictive vs the data.

Definition at line 216 of file SampleSummary.h.

◆ lnLHist_Sample_DrawData

std::vector<TH1D*> SampleSummary::lnLHist_Sample_DrawData
private

The histogram containing the lnL (draw vs data) for each throw for each sample.

Definition at line 192 of file SampleSummary.h.

◆ lnLHist_Sample_DrawflucDraw

std::vector<TH1D*> SampleSummary::lnLHist_Sample_DrawflucDraw
private

The histogram containing the lnL (draw vs draw fluct) for each throw for each sample.

Definition at line 194 of file SampleSummary.h.

◆ lnLHist_Sample_PredflucDraw

std::vector<TH1D*> SampleSummary::lnLHist_Sample_PredflucDraw
private

The histogram containing the lnL (draw vs pred fluct) for each throw for each sample.

Definition at line 196 of file SampleSummary.h.

◆ maxBins

std::vector<int> SampleSummary::maxBins
private

Max Number of Bins per each sample.

Definition at line 239 of file SampleSummary.h.

◆ MCVector

std::vector<std::vector<TH2Poly*> > SampleSummary::MCVector
private

Vector of vectors which holds the loaded MC histograms.

Definition at line 131 of file SampleSummary.h.

◆ MCVectorByMode

std::vector<std::vector<std::vector<TH2Poly*> > > SampleSummary::MCVectorByMode
private

Vector of vectors which holds the loaded MC histograms for each mode.

Definition at line 135 of file SampleSummary.h.

◆ MeanHist

std::vector<TH2Poly*> SampleSummary::MeanHist
private

The posterior predictive distribution in pmu cosmu using the mean.

Definition at line 207 of file SampleSummary.h.

◆ MeanHist_ByMode

std::vector<std::vector<TH2Poly*> > SampleSummary::MeanHist_ByMode
private

The posterior predictive distribution in pmu cosmu using the mean.

Definition at line 323 of file SampleSummary.h.

◆ MeanHistCorrected

std::vector<TH2Poly*> SampleSummary::MeanHistCorrected
private

The posterior predictive distribution in pmu cosmu using the mean after applying Barlow-Beeston Correction.

Definition at line 209 of file SampleSummary.h.

◆ ModeHist

std::vector<TH2Poly*> SampleSummary::ModeHist
private

The posterior predictive distribution in pmu cosmu using the mode.

Definition at line 211 of file SampleSummary.h.

◆ Modes

MaCh3Modes* SampleSummary::Modes
private

MaCh3 Modes.

Definition at line 331 of file SampleSummary.h.

◆ nChainSteps

unsigned int SampleSummary::nChainSteps
private

Number of throws by user.

Definition at line 227 of file SampleSummary.h.

◆ nModelParams

int SampleSummary::nModelParams
private

Number of parameters.

Definition at line 337 of file SampleSummary.h.

◆ NominalHist

std::vector<TH2Poly*> SampleSummary::NominalHist
private

The nominal histogram for the selection.

Definition at line 165 of file SampleSummary.h.

◆ nSamples

int SampleSummary::nSamples
private

Number of samples.

Definition at line 143 of file SampleSummary.h.

◆ nThrows

unsigned int SampleSummary::nThrows
private

Number of throws.

Definition at line 236 of file SampleSummary.h.

◆ Outputfile

TFile* SampleSummary::Outputfile
private

Output filename.

Definition at line 247 of file SampleSummary.h.

◆ OutputName

std::string SampleSummary::OutputName
private

Output filename.

Definition at line 245 of file SampleSummary.h.

◆ OutputTree

TTree* SampleSummary::OutputTree
private

TTree which we save useful information to.

Definition at line 252 of file SampleSummary.h.

◆ PosteriorHist

std::vector<std::vector<std::unique_ptr<TH1D> > > SampleSummary::PosteriorHist
private

The posterior predictive for the whole selection: this gets built after adding in the toys. Now an array of Th1ds, 1 for each poly bin, for each sample.

Definition at line 149 of file SampleSummary.h.

◆ PosteriorHist_ByMode

TH1D**** SampleSummary::PosteriorHist_ByMode
private

Histogram which corresponds to each bin in the sample's th2poly.

Definition at line 325 of file SampleSummary.h.

◆ RandomHist

std::unique_ptr<TH1D> SampleSummary::RandomHist
private

Holds the history of which entries have been drawn in the MCMC file.

Definition at line 219 of file SampleSummary.h.

◆ rnd

std::unique_ptr<TRandom3> SampleSummary::rnd
private

Random number generator.

Definition at line 123 of file SampleSummary.h.

◆ SampleHandler

SampleHandlerInterface* SampleSummary::SampleHandler
private

Pointer to SampleHandler object, mostly used to get sample names, binning etc.

Definition at line 328 of file SampleSummary.h.

◆ SampleNames

std::vector<std::string> SampleSummary::SampleNames
private

name for each sample

Definition at line 146 of file SampleSummary.h.

◆ StandardFluctuation

bool SampleSummary::StandardFluctuation
private

KS: We have two methods for Poissonian fluctuation.

Definition at line 128 of file SampleSummary.h.

◆ total_llh_data_draw

double SampleSummary::total_llh_data_draw
private

Data vs Draw.

Definition at line 289 of file SampleSummary.h.

◆ total_llh_data_draw_ProjectX

double SampleSummary::total_llh_data_draw_ProjectX
private

Data vs Draw for projection X (most likely muon momentum)

Definition at line 316 of file SampleSummary.h.

◆ total_llh_data_drawfluc

double SampleSummary::total_llh_data_drawfluc
private

Data vs Fluctuated Draw.

Definition at line 303 of file SampleSummary.h.

◆ total_llh_data_predfluc

double SampleSummary::total_llh_data_predfluc
private

Data vs Fluctuated Predictive.

Definition at line 301 of file SampleSummary.h.

◆ total_llh_datafluc_draw

double SampleSummary::total_llh_datafluc_draw
private

Fluctuated Data vs Draw.

Definition at line 311 of file SampleSummary.h.

◆ total_llh_draw_pred

double SampleSummary::total_llh_draw_pred
private

Draw vs Predictive.

Definition at line 305 of file SampleSummary.h.

◆ total_llh_drawfluc_draw

double SampleSummary::total_llh_drawfluc_draw
private

Fluctuated Draw vs Draw.

Definition at line 291 of file SampleSummary.h.

◆ total_llh_drawfluc_draw_ProjectX

double SampleSummary::total_llh_drawfluc_draw_ProjectX
private

Fluctuated Draw vs Draw for projection X (most likely muon momentum)

Definition at line 318 of file SampleSummary.h.

◆ total_llh_drawfluc_pred

double SampleSummary::total_llh_drawfluc_pred
private

Fluctuated Draw vs Predictive.

Definition at line 307 of file SampleSummary.h.

◆ total_llh_drawfluc_predfluc

double SampleSummary::total_llh_drawfluc_predfluc
private

Fluctuated Draw vs Fluctuated Predictive.

Definition at line 309 of file SampleSummary.h.

◆ total_llh_predfluc_draw

double SampleSummary::total_llh_predfluc_draw
private

Fluctuated Predictive vs Draw.

Definition at line 293 of file SampleSummary.h.

◆ total_llh_predfluc_pred

double SampleSummary::total_llh_predfluc_pred
private

Fluctuated Predictive vs Predictive.

Definition at line 313 of file SampleSummary.h.

◆ total_llh_rate_data_draw

double SampleSummary::total_llh_rate_data_draw
private

Rate Data vs Draw.

Definition at line 296 of file SampleSummary.h.

◆ total_llh_rate_predfluc_draw

double SampleSummary::total_llh_rate_predfluc_draw
private

Fluctuated Predictive vs Draw using Rate.

Definition at line 298 of file SampleSummary.h.

◆ ViolinHists_ProjectX

std::vector<TH2D*> SampleSummary::ViolinHists_ProjectX
private

Posterior predictive but for X projection but as a violin plot.

Definition at line 154 of file SampleSummary.h.

◆ ViolinHists_ProjectY

std::vector<TH2D*> SampleSummary::ViolinHists_ProjectY
private

Posterior predictive but for Y projection but as a violin plot.

Definition at line 156 of file SampleSummary.h.

◆ w2Hist

std::vector<std::vector<std::unique_ptr<TH1D> > > SampleSummary::w2Hist
private

The posterior predictive for the whole selection: this gets built after adding in the toys. Now an array of Th1ds, 1 for each poly bin, for each sample for W2.

Definition at line 151 of file SampleSummary.h.

◆ W2MCVector

std::vector<std::vector<TH2Poly*> > SampleSummary::W2MCVector
private

Vector of vectors which holds the loaded W2 histograms.

Definition at line 133 of file SampleSummary.h.

◆ W2MeanHist

std::vector<TH2Poly*> SampleSummary::W2MeanHist
private

Pointer to the w2 histograms (for mean values).

Definition at line 169 of file SampleSummary.h.

◆ W2ModeHist

std::vector<TH2Poly*> SampleSummary::W2ModeHist
private

Pointer to the w2 histograms (for mode values).

Definition at line 171 of file SampleSummary.h.

◆ W2NomHist

std::vector<TH2Poly*> SampleSummary::W2NomHist
private

Pointer to the w2 histograms (for nominal values).

Definition at line 167 of file SampleSummary.h.

◆ WeightVector

std::vector<double> SampleSummary::WeightVector
private

Vector holding weight.

Definition at line 140 of file SampleSummary.h.


The documentation for this class was generated from the following files: