R3BROOT
R3B analysis software
Loading...
Searching...
No Matches
R3BNeulandCommonFunc.h
Go to the documentation of this file.
1#pragma once
2
3#include "R3BNeulandCommon.h"
4#include <R3BException.h>
5#include <Rtypes.h>
6#include <algorithm>
7#include <array>
8#include <boost/algorithm/string/classification.hpp>
9#include <boost/algorithm/string/split.hpp>
10#include <boost/algorithm/string/trim.hpp>
11#include <cstddef>
12#include <fairlogger/Logger.h>
13#include <fmt/format.h>
14#include <root/TH1.h>
15#include <string>
16#include <string_view>
17#include <utility>
18#include <vector>
19
20namespace R3B::Neuland
21{
22
23 class Common
24 {
25 public:
26 static constexpr auto GetBarVerticalDisplacement(int module_num) -> double
27 {
28 const auto bar_num = ((module_num - 1) % BarsPerPlane) + 1;
29 return (2 * bar_num - 1 - BarsPerPlane) / 2. * BarSize_XY;
30 }
31 static constexpr auto IsPlaneIDHorizontal(int plane_id) -> bool
32 {
33 return (plane_id % 2 == FirstHorizontalPlane);
34 }
35 static constexpr auto IsPlaneIDVertical(int plane_id) -> bool { return !IsPlaneIDHorizontal(plane_id); }
36 static constexpr auto ModuleID2PlaneID(int moduleID) -> int { return moduleID / BarsPerPlane; }
37 static constexpr auto ModuleID2PlaneNum(int moduleID) -> int { return ModuleID2PlaneID(moduleID) + 1; }
38 static constexpr auto ModuleNum2BarID(int module_num) -> int { return ((module_num - 1) % BarsPerPlane); }
39 static constexpr auto IsModuleNumHorizontal(int module_num) -> bool
40 {
41 return IsPlaneIDHorizontal(ModuleID2PlaneID(module_num - 1));
42 }
43 // planeNum, barNum and ModuleNum is 1-based
44 static constexpr auto Neuland_PlaneBar2ModuleNum(int planeNum, int barNum) -> int
45 {
46 return ((planeNum - 1) * BarsPerPlane) + barNum;
47 }
48 template <typename T = double>
49 static constexpr auto PlaneID2ZPos(int plane_id) -> T
50 {
51 return static_cast<T>((plane_id + 0.5) * BarSize_Z);
52 }
53 template <typename T = double>
54 static constexpr auto ModuleNum2ZPos(int module_num) -> T
55 {
56 return PlaneID2ZPos<T>(ModuleID2PlaneID(module_num - 1));
57 }
59 };
60
61#ifdef HAS_CPP_STANDARD_23
62 template <typename Option>
63 void parse_io_branch_names(const Option& option,
64 std::vector<std::string>& read,
65 int read_num,
66 std::vector<std::string>& write,
67 int write_num)
68 {
69 LOGP(info, "Task {:?} is enabled", option.name);
70 auto resolve_branch_names = [](const std::string& input, std::vector<std::string>& output) -> void
71 {
72 output.clear();
73 boost::split(output, input, boost::is_any_of(";"));
74 // trim the empty spaces
75 std::for_each(output.begin(), output.end(), [](auto& name) -> void { boost::trim(name); });
76 // erase empty names
77 std::erase(output, "");
78 };
79
80 resolve_branch_names(option.read, read);
81 if (read.size() != read_num)
82 {
83 throw R3B::logic_error(fmt::format(
84 "Task {:?} requires {} read branch(es) but only received {} branch(es)! Parsed string: {:?}",
85 option.name,
86 read_num,
87 read.size(),
88 option.read));
89 }
90 resolve_branch_names(option.write, write);
91 if (write.size() != write_num)
92 {
93 throw R3B::logic_error(fmt::format(
94 "Task {:?} requires {} write branch(es) but only received {} branch(es)! Parsed string: {:?}",
95 option.name,
96 read_num,
97 write.size(),
98 option.write));
99 }
100 }
101
102 constexpr auto trim_space(std::string_view input) -> std::string_view
103 {
104 auto pos = input.find_first_not_of(' ');
105 if (pos == std::string_view::npos)
106 {
107 return {};
108 }
109 auto output = input.substr(pos);
110 pos = output.find_last_not_of(' ');
111 if (pos == std::string_view::npos)
112 {
113 return {};
114 }
115 output = output.substr(0, pos + 1);
116 return output;
117 }
118
119 constexpr auto get_from_sep_string(std::size_t target_idx, std::string_view input, std::string_view sep = ";")
120 -> std::string_view
121 {
122 auto idx = 0;
123 auto last_string = std::string_view{};
124 auto res_string = input;
125 while (std::cmp_less_equal(idx, target_idx))
126 {
127 auto pos = res_string.find_first_of(sep);
128 if (pos != std::string_view::npos)
129 {
130 last_string = trim_space(res_string.substr(0, pos));
131 res_string = res_string.substr(pos + 1);
132 }
133 else
134 {
135 return trim_space(res_string);
136 }
137 if (not last_string.empty())
138 {
139 ++idx;
140 }
141 }
142 return last_string;
143 }
144#endif
145
146 inline auto calculate_cdf(TH1* histogram) -> TH1*
147 {
148 histogram->Scale(1 / histogram->GetEntries());
149 auto* cumulative = histogram->GetCumulative();
150 histogram->Scale(histogram->GetEntries());
151 return cumulative;
152 }
153
154 inline auto calculate_hist_quantiles(TH1* histogram, double quantile_ratio) -> std::array<double, 2>
155 {
156 static constexpr auto QUANTILES_NUM = 2;
157 const auto quantiles =
158 std::array<double, QUANTILES_NUM>{ 0.5 - (quantile_ratio / 2.), 0.5 + (quantile_ratio / 2.) };
159 auto x_pos = std::array<double, QUANTILES_NUM>{};
160 histogram->GetQuantiles(QUANTILES_NUM, x_pos.data(), quantiles.data());
161 return x_pos;
162 }
163
164 inline auto calculate_CDF_with_quantiles(TH1* histogram, double ratio) -> std::pair<TH1*, std::array<double, 2>>
165 {
166 if (histogram == nullptr)
167 {
168 return {};
169 }
171 }
172
173} // namespace R3B::Neuland
static constexpr auto ModuleID2PlaneNum(int moduleID) -> int
static constexpr auto IsModuleNumHorizontal(int module_num) -> bool
static constexpr auto ModuleNum2BarID(int module_num) -> int
static constexpr auto ModuleID2PlaneID(int moduleID) -> int
static constexpr auto PlaneID2ZPos(int plane_id) -> T
static constexpr auto IsPlaneIDVertical(int plane_id) -> bool
static constexpr auto IsPlaneIDHorizontal(int plane_id) -> bool
static constexpr auto GetBarVerticalDisplacement(int module_num) -> double
static constexpr auto Neuland_PlaneBar2ModuleNum(int planeNum, int barNum) -> int
static constexpr auto ModuleNum2ZPos(int module_num) -> T
Simulation of NeuLAND Bar/Paddle.
auto calculate_hist_quantiles(TH1 *histogram, double quantile_ratio) -> std::array< double, 2 >
constexpr auto BarsPerPlane
auto calculate_CDF_with_quantiles(TH1 *histogram, double ratio) -> std::pair< TH1 *, std::array< double, 2 > >
constexpr auto BarSize_Z
constexpr auto BarSize_XY
constexpr auto FirstHorizontalPlane
auto calculate_cdf(TH1 *histogram) -> TH1 *