9#include <svd/calibration/SVDdEdxCalibrationAlgorithm.h>
10#include <svd/dbobjects/SVDdEdxPDFs.h>
23#include <RooDataSet.h>
24#include <RooRealVar.h>
26#include <RooGaussian.h>
27#include <RooChebychev.h>
28#include <RooBifurGauss.h>
29#include <RooDstD0BG.h>
30#include <RooAbsDataStore.h>
31#include <RooTreeDataStore.h>
32#include <RooMsgService.h>
33#include <RooStats/SPlot.h>
35using namespace RooFit;
47 gROOT->SetBatch(
true);
50 B2INFO(
"ExpRun used for calibration: " << exprun.first <<
" " << exprun.second);
55 auto ttreeLambda = getObjectPtr<TTree>(
"Lambda");
56 auto ttreeDstar = getObjectPtr<TTree>(
"Dstar");
57 auto ttreeGamma = getObjectPtr<TTree>(
"Gamma");
60 B2WARNING(
"Not enough data for calibration.");
66 auto [hDstarK, hDstarPi, hDstarMu] =
DstarMassFit(ttreeDstar);
70 for (
int pbin = 0; pbin <=
m_numPBins + 1; pbin++) {
71 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
72 hEmpty.SetBinContent(pbin, dedxbin, 0.01);
76 B2INFO(
"Histograms are ready, proceed to creating the payload object...");
77 std::vector<TH2F*> hDedxPDFs(6);
79 std::array<std::string, 6> part = {
"Electron",
"Muon",
"Pion",
"Kaon",
"Proton",
"Deuteron"};
81 TCanvas* candEdx =
new TCanvas(
"candEdx",
"SVD dEdx payloads", 1200, 700);
82 candEdx->Divide(3, 2);
83 gStyle->SetOptStat(11);
85 for (
bool trunmean : {
false,
true}) {
86 for (
int iPart = 0; iPart < 6; iPart++) {
88 if (iPart == 0 && trunmean) {
89 hDedxPDFs[iPart] = &hGammaE;
90 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
91 }
else if (iPart == 1 && trunmean) {
92 hDedxPDFs[iPart] = &hDstarMu;
93 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
94 }
else if (iPart == 2 && trunmean) {
95 hDedxPDFs[iPart] = &hDstarPi;
96 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
97 }
else if (iPart == 3 && trunmean) {
98 hDedxPDFs[iPart] = &hDstarK;
99 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
100 }
else if (iPart == 4 && trunmean) {
101 hDedxPDFs[iPart] = &hLambdaP;
102 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
103 }
else if (iPart == 5 && trunmean) {
104 hDedxPDFs[iPart] = &hEmpty;
105 hDedxPDFs[iPart]->SetName(
"hist_d1_1000010020_trunc");
106 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
107 }
else if (iPart == 0 && !trunmean) {
108 hDedxPDFs[iPart] = &hEmpty;
109 hDedxPDFs[iPart]->SetName(
"hist_d1_11");
110 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
111 }
else if (iPart == 1 && !trunmean) {
112 hDedxPDFs[iPart] = &hEmpty;
113 hDedxPDFs[iPart]->SetName(
"hist_d1_13");
114 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
115 }
else if (iPart == 2 && !trunmean) {
116 hDedxPDFs[iPart] = &hEmpty;
117 hDedxPDFs[iPart]->SetName(
"hist_d1_211");
118 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
119 }
else if (iPart == 3 && !trunmean) {
120 hDedxPDFs[iPart] = &hEmpty;
121 hDedxPDFs[iPart]->SetName(
"hist_d1_321");
122 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
123 }
else if (iPart == 4 && !trunmean) {
124 hDedxPDFs[iPart] = &hEmpty;
125 hDedxPDFs[iPart]->SetName(
"hist_d1_2212");
126 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
127 }
else if (iPart == 5 && !trunmean) {
128 hDedxPDFs[iPart] = &hEmpty;
129 hDedxPDFs[iPart]->SetName(
"hist_d1_1000010020");
130 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
134 hDedxPDFs[iPart] = &hEmpty;
135 payload->setPDF(*hDedxPDFs[iPart], iPart, trunmean);
137 candEdx->cd(iPart + 1);
138 hDedxPDFs[iPart]->SetTitle(Form(
"%s; p(GeV/c) of %s; dE/dx", hDedxPDFs[iPart]->GetTitle(), part[iPart].data()));
139 hDedxPDFs[iPart]->DrawCopy(
"colz");
142 candEdx->SaveAs(
"PlotsSVDdEdxPDFs_wTruncMean.pdf");
149 B2INFO(
"SVD dE/dx calibration done!");
156 B2INFO(
"Configuring the Lambda fit...");
157 gROOT->SetBatch(
true);
158 RooMsgService::instance().setGlobalKillBelow(RooFit::WARNING);
160 RooRealVar InvM(
"InvM",
"m(p^{+}#pi^{-})", 1.1, 1.13,
"GeV/c^{2}");
162 RooRealVar ProtonMomentum(
"ProtonMomentum",
"momentum for p", -1.e8, 1.e8);
163 RooRealVar ProtonSVDdEdx(
"ProtonSVDdEdx",
"", -1.e8, 1.e8);
165 RooRealVar exp(
"exp",
"experiment number", 0, 1.e5);
166 RooRealVar run(
"run",
"run number", 0, 1.e7);
168 auto variables =
new RooArgSet();
170 variables->add(InvM);
172 variables->add(ProtonMomentum);
173 variables->add(ProtonSVDdEdx);
177 RooDataSet* LambdaDataset =
new RooDataSet(
"LambdaDataset",
"LambdaDataset", preselTree.get(), *variables);
179 if (LambdaDataset->sumEntries() == 0) {
180 B2FATAL(
"The Lambda dataset is empty, stopping here");
185 RooRealVar GaussMean(
"GaussMean",
" GaussMean", 1.116, 1.111, 1.12);
186 RooRealVar GaussSigma(
"GaussSigma",
"#sigma_{1}", 3.e-3, 3.e-5, 10.e-3);
187 RooGaussian LambdaGauss(
"LambdaGauss",
"LambdaGauss", InvM, GaussMean, GaussSigma);
195 RooRealVar sigmaBifurGaussL1(
"sigmaBifurGaussL1",
"sigma left", 0.4 * 3.e-3, 3.e-5, 10.e-3);
196 RooRealVar sigmaBifurGaussR1(
"sigmaBifurGaussR1",
"sigma right", 0.4 * 3.e-3, 3.e-5, 10.e-3);
197 RooBifurGauss LambdaBifurGauss(
"LambdaBifurGauss",
"LambdaBifurGauss", InvM, GaussMean, sigmaBifurGaussL1, sigmaBifurGaussR1);
203 RooRealVar sigmaBifurGaussL2(
"sigmaBifurGaussL2",
"sigmaBifurGaussL2", 0.2 * 3.e-3, 3.e-5, 10.e-3);
204 RooGaussian LambdaBifurGauss2(
"LambdaBifurGauss2",
"LambdaBifurGauss2", InvM, GaussMean, sigmaBifurGaussL2);
206 RooRealVar fracBifurGaussYield(
"fracBifurGaussYield",
"fracBifurGaussYield", 0.3, 5.e-4, 1.0);
207 RooRealVar fracGaussYield(
"fracGaussYield",
"fracGaussYield", 0.8, 5.e-4, 1.0);
209 RooAddPdf LambdaCombinedBifurGauss(
"LambdaCombinedBifurGauss",
"LambdaBifurGauss + LambdaBifurGauss2 ", RooArgList(LambdaBifurGauss,
210 LambdaBifurGauss2), RooArgList(fracBifurGaussYield));
212 RooAddPdf LambdaSignalPDF(
"LambdaSignalPDF",
"LambdaCombinedBifurGauss + LambdaGauss", RooArgList(LambdaCombinedBifurGauss,
213 LambdaGauss), RooArgList(fracGaussYield));
216 RooRealVar BkgPolyCoef0(
"BkgPolyCoef0",
"BkgPolyCoef0", 0.1, 0., 1.5);
217 RooRealVar BkgPolyCoef1(
"BkgPolyCoef1",
"BkgPolyCoef1", -0.5, -1.5, -1.e-3);
218 RooChebychev BkgPolyPDF(
"BkgPolyPDF",
"BkgPolyPDF", InvM, RooArgList(BkgPolyCoef0, BkgPolyCoef1));
220 RooRealVar nSignalLambda(
"nSignalLambda",
"nSignalLambda", 0.6 * preselTree->GetEntries(), 0., 0.99 * preselTree->GetEntries());
221 RooRealVar nBkgLambda(
"nBkgLambda",
"nBkgLambda", 0.4 * preselTree->GetEntries(), 0., 0.99 * preselTree->GetEntries());
222 RooAddPdf totalPDFLambda(
"totalPDFLambda",
"totalPDFLambda pdf", RooArgList(LambdaSignalPDF, BkgPolyPDF),
223 RooArgList(nSignalLambda, nBkgLambda));
225 B2INFO(
"Lambda: Start fitting...");
226 RooFitResult* LambdaFitResult = totalPDFLambda.fitTo(*LambdaDataset, Save(kTRUE), PrintLevel(-1));
228 int status = LambdaFitResult->status();
229 int covqual = LambdaFitResult->covQual();
230 double diff = nSignalLambda.getValV() + nBkgLambda.getValV() - LambdaDataset->sumEntries();
232 B2INFO(
"Lambda: Fit status: " << status <<
"; covariance quality: " << covqual);
234 if ((status > 0) || (TMath::Abs(diff) > 1.) || (nSignalLambda.getError() <
sqrt(nSignalLambda.getValV()))
235 || (nSignalLambda.getError() > (nSignalLambda.getValV()))) {
237 LambdaFitResult = totalPDFLambda.fitTo(*LambdaDataset, Save(), Strategy(2), Offset(1));
238 status = LambdaFitResult->status();
239 covqual = LambdaFitResult->covQual();
240 diff = nSignalLambda.getValV() + nBkgLambda.getValV() - LambdaDataset->sumEntries();
243 if ((status > 0) || (TMath::Abs(diff) > 1.) || (nSignalLambda.getError() <
sqrt(nSignalLambda.getValV()))
244 || (nSignalLambda.getError() > (nSignalLambda.getValV()))) {
245 B2WARNING(
"Lambda: Fit problem: fit status " << status <<
"; sum of component yields minus the dataset yield is " << diff <<
246 "; signal yield is " << nSignalLambda.getValV() <<
", while its uncertainty is " << nSignalLambda.getError());
249 B2INFO(
"Lambda: Fit warning: covariance quality " << covqual);
252 TCanvas* canvLambda =
new TCanvas(
"canvLambda",
"canvLambda");
253 RooPlot* LambdaFitFrame = LambdaDataset->plotOn(InvM.frame(130));
254 totalPDFLambda.plotOn(LambdaFitFrame, LineColor(TColor::GetColor(
"#4575b4")));
256 double chisquare = LambdaFitFrame->chiSquare();
257 B2INFO(
"Lambda: Fit chi2 = " << chisquare);
258 totalPDFLambda.paramOn(LambdaFitFrame, Layout(0.6, 0.96, 0.93), Format(
"NEU", AutoPrecision(2)));
259 LambdaFitFrame->getAttText()->SetTextSize(0.03);
261 totalPDFLambda.plotOn(LambdaFitFrame, Components(
"LambdaSignalPDF"), LineColor(TColor::GetColor(
"#d73027")));
262 totalPDFLambda.plotOn(LambdaFitFrame, Components(
"BkgPolyPDF"), LineColor(TColor::GetColor(
"#fc8d59")));
263 totalPDFLambda.plotOn(LambdaFitFrame, LineColor(TColor::GetColor(
"#4575b4")));
265 LambdaFitFrame->GetXaxis()->SetTitle(
"m(p#pi^{-}) (GeV/c^{2})");
267 LambdaFitFrame->Draw();
270 canvLambda->Print(
"SVDdEdxCalibrationFitLambda.pdf");
271 TFile LambdaFitPlotFile(
"SVDdEdxCalibrationLambdaFitPlotFile.root",
"RECREATE");
273 LambdaFitPlotFile.Close();
275 RooStats::SPlot* sPlotDatasetLambda =
new RooStats::SPlot(
"sData",
"An SPlot", *LambdaDataset, &totalPDFLambda,
276 RooArgList(nSignalLambda, nBkgLambda));
278 for (
int iEvt = 0; iEvt < 5; iEvt++) {
279 if (TMath::Abs(sPlotDatasetLambda->GetSWeight(iEvt,
"nSignalLambda") + sPlotDatasetLambda->GetSWeight(iEvt,
280 "nBkgLambda") - 1) > 5.e-3)
281 B2FATAL(
"Lambda: sPlot error: sum of weights not equal to 1");
284 RooDataSet* LambdaDatasetSWeighted =
new RooDataSet(LambdaDataset->GetName(), LambdaDataset->GetTitle(), LambdaDataset,
285 *LambdaDataset->get());
287 RooDataSet::setDefaultStorageType(RooAbsData::Tree);
288 ((RooTreeDataStore*)(LambdaDatasetSWeighted->store())->tree())->SetName(
"treeLambda_sw");
289 TTree* treeLambda_sw = LambdaDatasetSWeighted->GetClonedTree();
291 B2INFO(
"Lambda: sPlot done. Proceed to histogramming");
297 treeLambda_sw->Draw(
"ProtonSVDdEdx:ProtonMomentum>>hist_d1_2212_trunc",
298 "nSignalLambda_sw * (ProtonMomentum>0.15) * (ProtonSVDdEdx>0)",
"goff");
302 TH1F* ProtonProfile = (TH1F*)hLambdaP->ProfileX(
"ProtonProfile");
303 ProtonProfile->SetTitle(
"ProtonProfile");
304 canvLambda->SetTicky(1);
305 ProtonProfile->GetYaxis()->SetRangeUser(0,
m_dedxCutoff);
306 ProtonProfile->GetXaxis()->SetTitle(
"Momentum, GeV/c");
307 ProtonProfile->GetYaxis()->SetTitle(
"dE/dx");
308 ProtonProfile->Draw();
309 canvLambda->Print(
"SVDdEdxCalibrationProfileProton.pdf");
310 TFile ProtonProfileFile(
"SVDdEdxCalibrationProfileProton.root",
"RECREATE");
311 ProtonProfile->Write();
312 ProtonProfileFile.Close();
313 canvLambda->SetTicky(0);
319 for (
int pbin = 0; pbin <=
m_numPBins + 1; pbin++) {
320 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
322 if (hLambdaP->GetBinContent(pbin, dedxbin) <= 1) {
323 hLambdaP->SetBinContent(pbin, dedxbin, 0);
327 TH1D*
slice = (TH1D*)hLambdaP->ProjectionY(
"slice", pbin, pbin);
329 if (
slice->Integral() > 0) {
333 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
334 hLambdaP->SetBinContent(pbin, dedxbin,
slice->GetBinContent(dedxbin));
339 hLambdaP->Draw(
"COLZ");
340 canvLambda->Print(
"SVDdEdxCalibrationHistoLambda.pdf");
348 B2INFO(
"Configuring the Dstar fit...");
349 gROOT->SetBatch(
true);
350 RooMsgService::instance().setGlobalKillBelow(RooFit::WARNING);
352 RooRealVar deltaM(
"deltaM",
"m(D*)-m(D^{0})", 0.139545, 0.151,
"GeV/c^{2}");
354 RooRealVar KaonMomentum(
"KaonMomentum",
"momentum for Kaon(GeV)", -1.e8, 1.e8);
355 RooRealVar KaonSVDdEdx(
"KaonSVDdEdx",
"", -1.e8, 1.e8);
356 RooRealVar PionDMomentum(
"PionDMomentum",
"momentum for pion(GeV)", -1.e8, 1.e8);
357 RooRealVar PionDSVDdEdx(
"PionDSVDdEdx",
"", -1.e8, 1.e8);
358 RooRealVar SlowPionMomentum(
"SlowPionMomentum",
"momentum for slow pion(GeV)", -1.e8, 1.e8);
359 RooRealVar SlowPionSVDdEdx(
"SlowPionSVDdEdx",
"", -1.e8, 1.e8);
361 RooRealVar exp(
"exp",
"experiment number", 0, 1.e5);
362 RooRealVar run(
"run",
"run number", 0, 1.e8);
364 auto variables =
new RooArgSet();
365 variables->add(deltaM);
366 variables->add(KaonMomentum);
367 variables->add(KaonSVDdEdx);
368 variables->add(PionDMomentum);
369 variables->add(PionDSVDdEdx);
370 variables->add(SlowPionMomentum);
371 variables->add(SlowPionSVDdEdx);
375 RooDataSet* DstarDataset =
new RooDataSet(
"DstarDataset",
"DstarDataset", preselTree.get(), *variables);
377 if (DstarDataset->sumEntries() == 0) {
378 B2FATAL(
"The Dstar dataset is empty, stopping here");
381 RooPlot* DstarFitFrame = DstarDataset->plotOn(deltaM.frame());
383 RooRealVar GaussMean(
"GaussMean",
"GaussMean", 0.145, 0.140, 0.150);
384 RooRealVar GaussSigma1(
"GaussSigma1",
"GaussSigma1", 0.01, 1.e-4, 1.0);
385 RooGaussian DstarGauss1(
"DstarGauss1",
"DstarGauss1", deltaM, GaussMean, GaussSigma1);
386 RooRealVar GaussSigma2(
"GaussSigma2",
"GaussSigma2", 0.001, 1.e-4, 1.0);
387 RooGaussian DstarGauss2(
"DstarGauss2",
"DstarGauss2", deltaM, GaussMean, GaussSigma2);
388 RooRealVar fracGaussYield(
"fracGaussYield",
"Fraction of two Gaussians", 0.75, 0.0, 1.0);
389 RooAddPdf DstarSignalPDF(
"DstarSignalPDF",
"DstarGauss1+DstarGauss2", RooArgList(DstarGauss1, DstarGauss2), fracGaussYield);
391 RooRealVar dm0Bkg(
"dm0Bkg",
"dm0", 0.13957018, 0.130, 0.140);
392 RooRealVar aBkg(
"aBkg",
"a", -0.0784, -0.08, 3.0);
393 RooRealVar bBkg(
"bBkg",
"b", -0.444713, -0.5, 0.4);
394 RooRealVar cBkg(
"cBkg",
"c", 0.3);
395 RooDstD0BG DstarBkgPDF(
"DstarBkgPDF",
"DstarBkgPDF", deltaM, dm0Bkg, cBkg, aBkg, bBkg);
396 RooRealVar nSignalDstar(
"nSignalDstar",
"signal yield", 0.5 * preselTree->GetEntries(), 0, preselTree->GetEntries());
397 RooRealVar nBkgDstar(
"nBkgDstar",
"background yield", 0.5 * preselTree->GetEntries(), 0, preselTree->GetEntries());
398 RooAddPdf totalPDFDstar(
"totalPDFDstar",
"totalPDFDstar pdf", RooArgList(DstarSignalPDF, DstarBkgPDF),
399 RooArgList(nSignalDstar, nBkgDstar));
401 B2INFO(
"Dstar: Start fitting...");
402 RooFitResult* DstarFitResult = totalPDFDstar.fitTo(*DstarDataset, Save(kTRUE), PrintLevel(-1));
404 int status = DstarFitResult->status();
405 int covqual = DstarFitResult->covQual();
406 double diff = nSignalDstar.getValV() + nBkgDstar.getValV() - DstarDataset->sumEntries();
408 B2INFO(
"Dstar: Fit status: " << status <<
"; covariance quality: " << covqual);
410 if ((status > 0) || (TMath::Abs(diff) > 1.) || (nSignalDstar.getError() <
sqrt(nSignalDstar.getValV()))
411 || (nSignalDstar.getError() > (nSignalDstar.getValV()))) {
413 DstarFitResult = totalPDFDstar.fitTo(*DstarDataset, Save(), Strategy(2), Offset(1));
414 status = DstarFitResult->status();
415 covqual = DstarFitResult->covQual();
416 diff = nSignalDstar.getValV() + nBkgDstar.getValV() - DstarDataset->sumEntries();
419 if ((status > 0) || (TMath::Abs(diff) > 1.) || (nSignalDstar.getError() <
sqrt(nSignalDstar.getValV()))
420 || (nSignalDstar.getError() > (nSignalDstar.getValV()))) {
421 B2WARNING(
"Dstar: Fit problem: fit status " << status <<
"; sum of component yields minus the dataset yield is " << diff <<
422 "; signal yield is " << nSignalDstar.getValV() <<
", while its uncertainty is " << nSignalDstar.getError());
425 B2INFO(
"Dstar: Fit warning: covariance quality " << covqual);
428 totalPDFDstar.plotOn(DstarFitFrame, LineColor(TColor::GetColor(
"#4575b4")));
430 double chisquare = DstarFitFrame->chiSquare();
431 B2INFO(
"Dstar: Fit chi2 = " << chisquare);
432 totalPDFDstar.paramOn(DstarFitFrame, Layout(0.63, 0.96, 0.93), Format(
"NEU", AutoPrecision(2)));
433 DstarFitFrame->getAttText()->SetTextSize(0.03);
435 totalPDFDstar.plotOn(DstarFitFrame, Components(
"DstarSignalPDF"), LineColor(TColor::GetColor(
"#d73027")));
436 totalPDFDstar.plotOn(DstarFitFrame, Components(
"DstarBkgPDF"), LineColor(TColor::GetColor(
"#fc8d59")));
437 totalPDFDstar.plotOn(DstarFitFrame, LineColor(TColor::GetColor(
"#4575b4")));
439 DstarFitFrame->GetXaxis()->SetTitle(
"#Deltam [GeV/c^{2}]");
440 TCanvas* canvDstar =
new TCanvas(
"canvDstar",
"canvDstar");
443 DstarFitFrame->Draw();
446 canvDstar->Print(
"SVDdEdxCalibrationFitDstar.pdf");
447 TFile DstarFitPlotFile(
"SVDdEdxCalibrationDstarFitPlotFile.root",
"RECREATE");
449 DstarFitPlotFile.Close();
454 RooStats::SPlot* sPlotDatasetDstar =
new RooStats::SPlot(
"sData",
"An SPlot", *DstarDataset, &totalPDFDstar,
455 RooArgList(nSignalDstar, nBkgDstar));
457 for (
int iEvt = 0; iEvt < 5; iEvt++) {
458 if (TMath::Abs(sPlotDatasetDstar->GetSWeight(iEvt,
"nSignalDstar") + sPlotDatasetDstar->GetSWeight(iEvt,
"nBkgDstar") - 1) > 5.e-3)
459 B2FATAL(
"Dstar: sPlot error: sum of weights not equal to 1");
462 RooDataSet* DstarDatasetSWeighted =
new RooDataSet(DstarDataset->GetName(), DstarDataset->GetTitle(), DstarDataset,
463 *DstarDataset->get());
465 RooDataSet::setDefaultStorageType(RooAbsData::Tree);
466 ((RooTreeDataStore*)(DstarDatasetSWeighted->store())->tree())->SetName(
"treeDstar_sw");
467 TTree* treeDstar_sw = DstarDatasetSWeighted->GetClonedTree();
469 B2INFO(
"Dstar: sPlot done. Proceed to histogramming");
474 TH2F* hDstarK =
new TH2F(
"hist_d1_321_trunc",
"hist_d1_321_trunc",
m_numPBins, pbins.data(),
477 TH2F* hDstarPi =
new TH2F(
"hist_d1_211_trunc",
"hist_d1_211_trunc",
m_numPBins, pbins.data(),
480 treeDstar_sw->Draw(
"KaonSVDdEdx:KaonMomentum>>hist_d1_321_trunc",
"nSignalDstar_sw * (KaonSVDdEdx>0)",
"goff");
482 TH2F* hDstarPiPart1 = (TH2F*)hDstarPi->Clone(
"hist_d1_211_truncPart1");
483 TH2F* hDstarPiPart2 = (TH2F*)hDstarPi->Clone(
"hist_d1_211_truncPart2");
485 treeDstar_sw->Draw(
"PionDSVDdEdx:PionDMomentum>>hist_d1_211_truncPart1",
"nSignalDstar_sw * (PionDSVDdEdx>0)",
"goff");
486 treeDstar_sw->Draw(
"SlowPionSVDdEdx:SlowPionMomentum>>hist_d1_211_truncPart2",
"nSignalDstar_sw * (SlowPionSVDdEdx>0)",
"goff");
487 hDstarPi->Add(hDstarPiPart1);
488 hDstarPi->Add(hDstarPiPart2);
491 TH2F* hDstarMu = (TH2F*)hDstarPi->Clone(
"hist_d1_13_trunc");
492 hDstarMu->SetTitle(
"hist_d1_13_trunc");
496 TH1F* PionProfile = (TH1F*)hDstarPi->ProfileX(
"PionProfile");
497 PionProfile->SetTitle(
"PionProfile");
498 canvDstar->SetTicky(1);
500 PionProfile->GetXaxis()->SetTitle(
"Momentum, GeV/c");
501 PionProfile->GetYaxis()->SetTitle(
"dE/dx");
503 canvDstar->Print(
"SVDdEdxCalibrationProfilePion.pdf");
504 TFile PionProfileFile(
"SVDdEdxCalibrationProfilePion.root",
"RECREATE");
505 PionProfile->Write();
506 PionProfileFile.Close();
508 TH1F* KaonProfile = (TH1F*)hDstarK->ProfileX(
"KaonProfile");
509 KaonProfile->SetTitle(
"KaonProfile");
511 KaonProfile->GetXaxis()->SetTitle(
"Momentum, GeV/c");
512 KaonProfile->GetYaxis()->SetTitle(
"dE/dx");
514 canvDstar->Print(
"SVDdEdxCalibrationProfileKaon.pdf");
515 TFile KaonProfileFile(
"SVDdEdxCalibrationProfileKaon.root",
"RECREATE");
516 KaonProfile->Write();
517 KaonProfileFile.Close();
518 canvDstar->SetTicky(0);
524 for (
int pbin = 0; pbin <=
m_numPBins + 1; pbin++) {
525 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
527 if (hDstarK->GetBinContent(pbin, dedxbin) <= 1) {
528 hDstarK->SetBinContent(pbin, dedxbin, 0);
532 TH1D*
slice = (TH1D*)hDstarK->ProjectionY(
"slice", pbin, pbin);
534 if (
slice->Integral() > 0) {
538 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
539 hDstarK->SetBinContent(pbin, dedxbin,
slice->GetBinContent(dedxbin));
544 for (
int pbin = 0; pbin <=
m_numPBins + 1; pbin++) {
545 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
547 if (hDstarPi->GetBinContent(pbin, dedxbin) <= 1) {
548 hDstarPi->SetBinContent(pbin, dedxbin, 0);
552 TH1D*
slice = (TH1D*)hDstarPi->ProjectionY(
"slice", pbin, pbin);
554 if (
slice->Integral() > 0) {
558 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
559 hDstarPi->SetBinContent(pbin, dedxbin,
slice->GetBinContent(dedxbin));
564 for (
int pbin = 0; pbin <=
m_numPBins + 1; pbin++) {
565 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
567 if (hDstarMu->GetBinContent(pbin, dedxbin) <= 1) {
568 hDstarMu->SetBinContent(pbin, dedxbin, 0);
572 TH1D*
slice = (TH1D*)hDstarMu->ProjectionY(
"slice", pbin, pbin);
574 if (
slice->Integral() > 0) {
578 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
579 hDstarMu->SetBinContent(pbin, dedxbin,
slice->GetBinContent(dedxbin));
583 hDstarK->Draw(
"COLZ");
584 canvDstar->Print(
"SVDdEdxCalibrationHistoDstarK.pdf");
585 hDstarPi->Draw(
"COLZ");
586 canvDstar->Print(
"SVDdEdxCalibrationHistoDstarPi.pdf");
587 hDstarMu->Draw(
"COLZ");
588 canvDstar->Print(
"SVDdEdxCalibrationHistoDstarMu.pdf");
591 return std::make_tuple(*hDstarK, *hDstarPi, *hDstarMu);
596 B2INFO(
"Histogramming the converted photon selection...");
597 gROOT->SetBatch(
true);
599 if (preselTree->GetEntries() == 0) {
600 B2FATAL(
"The Gamma tree is empty, stopping here");
606 TH2F* hGammaEPart1 = (TH2F*)hGammaE->Clone(
"hist_d1_11_truncPart1");
607 TH2F* hGammaEPart2 = (TH2F*)hGammaE->Clone(
"hist_d1_11_truncPart2");
609 preselTree->Draw(
"FirstElectronSVDdEdx:FirstElectronMomentum>>hist_d1_11_truncPart1",
"FirstElectronSVDdEdx>0",
"goff");
610 preselTree->Draw(
"SecondElectronSVDdEdx:SecondElectronMomentum>>hist_d1_11_truncPart2",
"SecondElectronSVDdEdx>0",
"goff");
611 hGammaE->Add(hGammaEPart1);
612 hGammaE->Add(hGammaEPart2);
615 TCanvas* canvGamma =
new TCanvas(
"canvGamma",
"canvGamma");
617 TH1F* ElectronProfile = (TH1F*)hGammaE->ProfileX(
"ElectronProfile");
618 ElectronProfile->SetTitle(
"ElectronProfile");
619 canvGamma->SetTicky(1);
620 ElectronProfile->GetYaxis()->SetRangeUser(0,
m_dedxCutoff);
621 ElectronProfile->GetXaxis()->SetTitle(
"Momentum, GeV/c");
622 ElectronProfile->GetYaxis()->SetTitle(
"dE/dx");
623 ElectronProfile->Draw();
624 canvGamma->Print(
"SVDdEdxCalibrationProfileElectron.pdf");
625 TFile ElectronProfileFile(
"SVDdEdxCalibrationProfileElectron.root",
"RECREATE");
626 ElectronProfile->Write();
627 ElectronProfileFile.Close();
628 canvGamma->SetTicky(0);
633 for (
int pbin = 0; pbin <=
m_numPBins + 1; pbin++) {
634 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
636 if (hGammaE->GetBinContent(pbin, dedxbin) <= 1) {
637 hGammaE->SetBinContent(pbin, dedxbin, 0);
642 TH1D*
slice = (TH1D*)hGammaE->ProjectionY(
"slice", pbin, pbin);
644 if (
slice->Integral() > 0) {
648 for (
int dedxbin = 0; dedxbin <=
m_numDEdxBins + 1; dedxbin++) {
649 hGammaE->SetBinContent(pbin, dedxbin,
slice->GetBinContent(dedxbin));
654 hGammaE->Draw(
"COLZ");
655 canvGamma->Print(
"SVDdEdxCalibrationHistoGamma.pdf");
Base class for calibration algorithms.
void saveCalibration(TClonesArray *data, const std::string &name)
Store DBArray payload with given name with default IOV.
void setDescription(const std::string &description)
Set algorithm description (in constructor)
const std::vector< Calibration::ExpRun > & getRunList() const
Get the list of runs for which calibration is called.
EResult
The result of calibration.
@ c_OK
Finished successfully =0 in Python.
@ c_NotEnoughData
Needs more data =2 in Python.
std::tuple< TH2F, TH2F, TH2F > DstarMassFit(std::shared_ptr< TTree > preselTree)
produce histograms for K/pi(/mu)
int m_numPBins
the number of momentum bins for the payloads
std::vector< double > CreatePBinningScheme()
build the binning scheme
SVDdEdxCalibrationAlgorithm()
Constructor.
bool m_isMakePlots
produce plots for monitoring
int m_MinEvtsPerTree
number of events in TTree below which we don't try to fit
int m_numDEdxBins
the number of dEdx bins for the payloads
TH2F GammaHistogram(std::shared_ptr< TTree > preselTree)
produce histograms for e
virtual EResult calibrate() override
run algorithm on data
TH2F LambdaMassFit(std::shared_ptr< TTree > preselTree)
produce histograms for protons
double m_dedxCutoff
the upper edge of the dEdx binning for the payloads
Specialized class for holding the SVD dE/dx PDFs.
double sqrt(double a)
sqrt for double
std::vector< Atom > slice(std::vector< Atom > vec, int s, int e)
Slice the vector to contain only elements with indexes s .. e (included)
Abstract base class for different kinds of events.