11 #include "sbnanaobj/StandardRecord/Proxy/SRProxy.h"
13 #include "OscLib/IOscCalc.h"
15 #include "TDirectory.h"
18 #include "TObjString.h"
41 fCachedOsc(0, {}, {}, 0, 0),
44 fTrueLabel =
"True baseline / True energy (km / GeV)";
50 loader.AddReweightableSpectrum(*
this, var, cut,
shift, wei);
71 fCachedOsc(0, {}, {}, 0, 0),
74 fTrueLabel =
"True baseline / True energy (km / GeV)";
76 Binning bins1D =
fBins[0];
79 for(
const Binning& b:
fBins) n *= b.NBins();
84 for(
const std::string& l:
fLabels) label += l +
" and ";
85 label.resize(label.size()-5);
87 DontAddDirectory guard;
91 Var multiDVar = axis.GetVars()[0];
92 if(axis.NDimensions() == 2)
93 multiDVar =
Var2D(axis.GetVars()[0], axis.GetBinnings()[0],
94 axis.GetVars()[1], axis.GetBinnings()[1]);
95 if(axis.NDimensions() == 3)
96 multiDVar =
Var3D(axis.GetVars()[0], axis.GetBinnings()[0],
97 axis.GetVars()[1], axis.GetBinnings()[1],
98 axis.GetVars()[2], axis.GetBinnings()[2]);
100 loader.AddReweightableSpectrum(*
this, multiDVar, spillcut, slicecut,
shift, wei);
107 fCachedOsc(0, {}, {}, 0, 0),
110 fTrueLabel =
"True baseline / True energy (km / GeV)";
112 DontAddDirectory guard;
124 fCachedOsc(0, {}, {}, 0, 0),
127 fTrueLabel =
"True baseline / True energy (km / GeV)";
129 DontAddDirectory guard;
139 const std::vector<std::string>&
labels,
140 const std::vector<Binning>& bins,
141 double pot,
double livetime)
143 fCachedOsc(0, {}, {}, 0, 0),
146 fTrueLabel =
"True baseline / True energy (km / GeV)";
151 const std::vector<std::string>&
labels,
152 const std::vector<Binning>& bins,
153 double pot,
double livetime)
155 fCachedOsc(0, {}, {}, 0, 0),
158 fTrueLabel =
"True baseline / True energy (km / GeV)";
168 {
loader->RemoveReweightableSpectrum(
this); }
176 fCachedOsc(0, {}, {}, 0, 0),
179 DontAddDirectory guard;
191 assert( rhs.fLoaderCount.empty() );
197 fCachedOsc(0, {}, {}, 0, 0),
200 DontAddDirectory guard;
214 assert( rhs.fLoaderCount.empty() );
220 if(
this == &rhs)
return *
this;
246 if(
this == &rhs)
return *
this;
255 fLabels = rhs.fLabels;
265 assert( rhs.fLoaderCount.empty() );
273 int from,
int to)
const
277 const bool isLoverE = (
fHist->GetYaxis()->GetXmax() == 2);
278 static bool once =
true;
279 if(once && !isLoverE){
281 std::cout <<
"\nWarning: OscillatableSpectrum with legacy non-L/E y-axis detected. Will oscillate correctly for now, but this code will eventually be removed\n" << std::endl;
288 TMD5* hash = calc->GetParamsHash();
294 const OscCurve curve(calc, from, to, isLoverE);
295 TH1D* Ps = curve.
ToTH1();
318 assert(rhs.
fHist->Integral() == 0);
343 assert(rhs.
fHist->Integral() == 0);
363 TDirectory* tmp = gDirectory;
366 TObjString(
"OscillatableSpectrum").Write(
"type");
368 fHist->Write(
"hist");
369 TH1D hPot(
"",
"", 1, 0, 1);
372 TH1D hLivetime(
"",
"", 1, 0, 1);
374 hLivetime.Write(
"livetime");
376 for(
unsigned int i = 0; i < fBins.size(); ++i){
377 TObjString(fLabels[i].c_str()).Write(TString::Format(
"label%d", i).
Data());
378 fBins[i].SaveTo(dir->mkdir(TString::Format(
"bins%d", i)));
389 TObjString* tag = (TObjString*)dir->Get(
"type");
391 assert(tag->GetString() ==
"OscillatableSpectrum");
394 TH2D* spect = (TH2D*)dir->Get(
"hist");
396 TH1* hPot = (TH1*)dir->Get(
"pot");
398 TH1* hLivetime = (TH1*)dir->Get(
"livetime");
401 std::vector<std::string>
labels;
402 std::vector<Binning> bins;
404 for(
int i = 0; ; ++i){
405 TDirectory* subdir = dir->GetDirectory(TString::Format(
"bins%d", i));
408 TObjString* label = (TObjString*)dir->Get(TString::Format(
"label%d", i));
409 labels.push_back(label ? label->GetString().Data() :
"");
414 if(bins.empty() && labels.empty()){
417 labels.push_back(spect->GetXaxis()->GetTitle());
420 auto ret = std::make_unique<OscillatableSpectrum>(std::unique_ptr<TH2D>(spect),
422 hPot->GetBinContent(1),
423 hLivetime->GetBinContent(1));
double std(const std::vector< short > &wf, const double ped_mean, size_t start, size_t nsample)
Represent the binning of a Spectrum's x-axis.
static TH1D * Copy(const TH1D *h)
Simple record of shifts applied to systematic parameters.
static Binning FromTAxis(const TAxis *ax)
_Var< T > Var2D(const _Var< T > &a, const Binning &binsa, const _Var< T > &b, const Binning &binsb)
Variable formed from two input variables.
static std::unique_ptr< OscillatableSpectrum > LoadFrom(TDirectory *dir)
Spectrum with the value of a second variable, allowing for reweighting
const Binning kTrueLOverEBins
process_name opflashCryoW ana
OscillatableSpectrum & operator-=(const OscillatableSpectrum &rhs)
caf::Proxy< caf::SRSlice > SRSliceProxy
_Var< caf::SRSliceProxy > Var
Representation of a variable to be retrieved from a caf::StandardRecord object.
_Var< T > Var3D(const _Var< T > &a, const Binning &binsa, const _Var< T > &b, const Binning &binsb, const _Var< T > &c, const Binning &binsc)
This is just like a Var2D, but useful for 3D Spectra.
Representation of a spectrum in any variable, with associated POT.
OscillatableSpectrum(const std::string &label, const Binning &bins, SpectrumLoaderBase &loader, const Var &var, const Cut &cut, const SystShifts &shift=kNoShift, const Var &wei=kUnweighted)
static TH2D * NewTH2D(const std::string &title, const Binning &xbins, const Binning &ybins)
static void Delete(TH1D *&h)
TH1D * ToTH1(bool title=false) const
std::set< SpectrumLoaderBase * > fLoaderCount
This count is maintained by SpectrumLoader, as a sanity check.
const SpillCut kNoSpillCut([](const caf::SRSpillProxy *){return true;})
The simplest possible cut: pass everything, used as a default.
std::vector< std::string > fLabels
OscillatableSpectrum & operator+=(const OscillatableSpectrum &rhs)
OscillatableSpectrum operator+(const OscillatableSpectrum &rhs) const
Base class for the various types of spectrum loader.
Transition probability for any one channel as a function of energy.
Spectrum Oscillated(osc::IOscCalc *calc, int from, int to) const
Spectrum WeightedBy(const TH1 *weights) const
std::vector< Binning > fBins
OscillatableSpectrum & operator=(const OscillatableSpectrum &rhs)
Assignment operator.
Prevent histograms being added to the current directory.
Spectrum with true energy information, allowing it to be oscillated
OscillatableSpectrum operator-(const OscillatableSpectrum &rhs) const
static Binning Simple(int n, double lo, double hi, const std::vector< std::string > &labels={})
static std::unique_ptr< Binning > LoadFrom(TDirectory *dir)
BEGIN_PROLOG could also be cout
const Var kTrueE([](const caf::SRSliceProxy *slc) -> double{return slc->truth.E;})
void SaveTo(TDirectory *dir) const