Belle II Software development
CDCDedxInjectionTime.cc
1/**************************************************************************
2 * basf2 (Belle II Analysis Software Framework) *
3 * Author: The Belle II Collaboration *
4 * *
5 * See git log for contributors and copyright holders. *
6 * This file is licensed under LGPL-3.0, see LICENSE.md. *
7 **************************************************************************/
8
9#include <cdc/dbobjects/CDCDedxInjectionTime.h>
10
11#include <TCanvas.h>
12#include <TH1F.h>
13
14using namespace Belle2;
15
16void CDCDedxInjectionTime::printCorrection(std::string svar, std::string sfx) const
17{
18
19 if (svar != "mean" && svar != "reso") {
20 B2WARNING("wrong variable input, choose mean or reso");
21 return;
22 }
23
24 std::string sring[2] = {"ler", "her"};
25 TCanvas* cdraw = new TCanvas("cdraw", "cdraw", 900, 500);
26 cdraw->cd();
27 cdraw->SetGridy(1);
28
29 for (int ir = 0; ir < 2; ir++) {
30
31 unsigned int iv = ir * 3 + 1 ;
32 if (svar == "reso") iv = ir * 3 + 2 ;
33
34 unsigned int sizev = m_injectionvar[iv].size(); //mean or reso
35 unsigned int sizet = m_injectionvar[ir * 3].size(); //time
36 if (sizev == 0 || sizet == 0) {
37 B2ERROR("empty calibration vector");
38 break;
39 }
40
41 std::vector<unsigned int> tedges(sizet); //time edges array
42 std::copy(m_injectionvar[ir * 3].begin(), m_injectionvar[ir * 3].end(), tedges.begin());
43
44 std::string hname = Form("hconst_%s_%s_%s", svar.data(), sring[ir].data(), sfx.data());
45 std::string title = Form("%s corrections;injection-time (#mu-sec);%s", svar.data(), svar.data());
46 TH1F hconst(hname.data(), title.data(), sizet - 1, 0, sizet - 1);
47
48 for (unsigned int ib = 0; ib < sizev; ib++) {
49
50 double corr = m_injectionvar[iv].at(ib);
51 double ledge = tedges[ib];
52 double uedge = tedges[ib + 1];
53
54 std::string label;
55 if (ledge < 2e4)label = Form("%0.01f-%0.01fK", ledge / 1e3, uedge / 1e3);
56 else if (ledge < 1e5)label = Form("%0.00f-%0.00fK", ledge / 1e3, uedge / 1e3);
57 else label = Form("%0.01f-%0.01fM", ledge / 1e6, uedge / 1e6);
58
59 hconst.SetBinContent(ib + 1, corr);
60 hconst.SetBinError(ib + 1, corr * 0.001);
61 hconst.GetXaxis()->SetBinLabel(ib + 1, Form("%s", label.data()));
62 B2INFO("ring: " << sring[ir] << ", time (" << ledge << "-" << uedge << "), mean: " << corr << "");
63 }
64
65 hconst.SetStats(0);
66 hconst.SetMarkerColor(ir + 1);
67 hconst.SetMarkerSize(1.05);
68 hconst.SetMarkerStyle(24);
69 hconst.GetXaxis()->SetLabelOffset(-0.055);
70 hconst.GetYaxis()->SetRangeUser(0.60, 1.10);
71 if (svar == "reso")hconst.GetYaxis()->SetRangeUser(0.01, 0.20);
72
73 if (ir == 0)hconst.DrawCopy("");
74 else hconst.DrawCopy(" same");
75 }
76
77 cdraw->SaveAs(Form("cdcdedx_timeinject_const_%s_%s.pdf", svar.data(), sfx.data()));
78 delete cdraw;
79
80}
81
82
83double CDCDedxInjectionTime::getCorrection(std::string svar, unsigned int ring, unsigned int time) const
84{
85 if (svar != "mean" && svar != "reso") {
86 B2ERROR("wrong var input, choose mean or reso");
87 return 1.0;
88 }
89
90 if (ring > 1) {
91 B2ERROR("wrong ring input, choose 0 or 1");
92 return 1.0;
93 }
94
95 unsigned int iv = ring * 3 + 1 ;
96 if (svar == "reso") iv = ring * 3 + 2 ;
97
98 if (iv >= m_injectionvar.size()) return 1.0;
99
100 int sizev = m_injectionvar[iv].size(); //mean or reso
101 int sizet = m_injectionvar[ring * 3].size(); //time
102 if (sizet < 2 or sizev < 2) {
103 B2ERROR("calibration vectors are empty or have only a single element");
104 return 1.0;
105 }
106
107 std::vector<unsigned int> tedges(sizet); //time edges array
108 std::copy(m_injectionvar[ring * 3].begin(), m_injectionvar[ring * 3].end(), tedges.begin());
109
110 if (time >= 5e6) time = 5e6 - 10;
111
112 int it = getTimeBin(tedges, time);
113 if (it < 0) it = 0;
114
115 double center = 0.5 * (getSafely(ring * 3, it) + getSafely(ring * 3, it + 1));
116
117 //no corr before veto bin (usually one or two starting bin)
118 //intrapolation for entire range except
119 //--extrapolation (for first half and last half of intended bin)
120 int thisbin = it, nextbin = it;
121 if (center != time && it > 0) {
122
123 if (time < center) {
124 thisbin = it - 1;
125 } else {
126 if (it < sizet - 2) nextbin = it + 1;
127 else thisbin = it - 1;
128 }
129
130 if (it <= 2) {
131 double diff = getSafely(iv, 2) - getSafely(iv, 1) ;
132 if (diff < -0.015) { //difference above 1.0%
133 thisbin = it;
134 if (it == 1) nextbin = it;
135 else nextbin = it + 1;
136 } else {
137 if (it == 1) {
138 thisbin = it;
139 nextbin = it + 1;
140 }
141 }
142 }
143 }
144
145 double thisdedx = getSafely(iv, thisbin);
146 double nextdedx = getSafely(iv, nextbin);
147
148 double thistime = 0.5 * (getSafely(ring * 3, thisbin) + getSafely(ring * 3, thisbin + 1));
149 double nexttime = 0.5 * (getSafely(ring * 3, nextbin) + getSafely(ring * 3, nextbin + 1));
150
151 double newdedx = getSafely(iv, it);
152 if (thisbin != nextbin)
153 newdedx = thisdedx + ((nextdedx - thisdedx) / (nexttime - thistime)) * (time - thistime);
154
155 return newdedx;
156}
int getTimeBin(const std::vector< unsigned int > &array, unsigned int value) const
Return time bin for the given time array.
double getSafely(unsigned int iv, int k) const
Helper: safe access to a vector element.
void printCorrection(std::string svar, std::string sfx) const
Return dE/dx mean or norm-reso value for the given time and ring.
double getCorrection(std::string svar, unsigned int ring, unsigned int time) const
Return dE/dx mean or norm-reso value for the given time and ring.
std::vector< std::vector< double > > m_injectionvar
CDC dE/dx injection time payloads for dEdx mean and reso.
Abstract base class for different kinds of events.