Belle II Software development
AxialTrackCreatorHitHough.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#include <tracking/trackFindingCDC/findlets/minimal/AxialTrackCreatorHitHough.h>
9
10#include <tracking/trackFindingCDC/hough/perigee/AxialLegendreLeafProcessor.h>
11#include <tracking/trackFindingCDC/hough/perigee/AxialLegendreLeafProcessor.icc.h>
12#include <tracking/trackFindingCDC/hough/perigee/StandardBinSpec.h>
13
14#include <tracking/trackFindingCDC/eventdata/tracks/CDCTrack.h>
15#include <tracking/trackFindingCDC/eventdata/hits/CDCWireHit.h>
16
17#include <tracking/trackFindingCDC/utilities/StringManipulation.h>
18
19#include <framework/core/ModuleParamList.templateDetails.h>
20
21using namespace Belle2;
22using namespace TrackFindingCDC;
23
24#if 0
25namespace {
26 void saveBounds(std::vector<float> bounds, const std::string& fileName)
27 {
28 std::ofstream boundsFile;
29 boundsFile.open(fileName);
30 for (float bound : bounds) {
31 boundsFile << bound;
32 boundsFile << "\n";
33 }
34 boundsFile.close();
35 }
36
37 std::vector<float> loadBounds(const std::string& fileName)
38 {
39 std::vector<float> bounds;
40 std::ifstream boundsFile;
41 std::string boundLine;
42 boundsFile.open(fileName);
43 if (boundsFile.is_open()) {
44 while (std::getline(boundsFile, boundLine)) {
45 float bound = stof(boundLine);
46 bounds.push_back(bound);
47 }
48 boundsFile.close();
49 } else {
50 B2ERROR("Could not read bounds file");
51 }
52 return bounds;
53 }
54}
55#endif
56
58{
59 return "Generates axial tracks from hits using several increasingly relaxed hough space search over phi0 and curvature.";
60}
61
63 const std::string& prefix)
64{
65 // Parameters for the hough space
66 moduleParamList->addParameter(prefixed(prefix, "granularityLevel"),
68 "Level of divisions in the hough space.",
70
71 moduleParamList->addParameter(prefixed(prefix, "sectorLevelSkip"),
73 "Number of levels to be skipped in the hough "
74 "space on the first level to form sectors",
76
77 moduleParamList->addParameter(prefixed(prefix, "curvBounds"),
79 "Curvature bounds of the hough space. Either 2 or all discrete bounds",
81
82 moduleParamList->addParameter(prefixed(prefix, "discretePhi0Width"),
84 "Width of the phi0 bins at the lowest level of the hough space.",
86
87 moduleParamList->addParameter(prefixed(prefix, "discretePhi0Overlap"),
89 "Overlap of the phi0 bins at the lowest level of the hough space.",
91
92 moduleParamList->addParameter(prefixed(prefix, "discreteCurvWidth"),
94 "Width of the curvature bins at the lowest level of the hough space.",
96
97 moduleParamList->addParameter(prefixed(prefix, "discreteCurvOverlap"),
99 "Overlap of the curvature bins at the lowest level of the hough space.",
101
102 // Relaxation schedule
103 moduleParamList->addParameter(prefixed(prefix, "relaxationSchedule"),
105 "Relaxation schedule for the leaf processor in the hough tree. "
106 "For content of the individual parameter maps consider the parameters of the "
107 "AxialLegendreLeafProcessor",
109
110}
111
113{
115
116 // Construct the hough space
117 const long nPhi0Bins = std::pow(c_phi0Divisions, m_param_granularityLevel);
118 const Phi0BinsSpec phi0BinsSpec(nPhi0Bins,
121
122 if (m_param_curvBounds.size() == 2) {
123 // If parameters are unchanged use the legendre default binning
124 if (m_param_discreteCurvOverlap == -1) {
126 std::array<float, 2> curvSpan({m_param_curvBounds[0], m_param_curvBounds[1]});
128 } else {
129 std::array<double, 2> curvBounds{{m_param_curvBounds.front(), m_param_curvBounds.back()}};
130 const long nCurvBins = std::pow(c_curvDivisions, m_param_granularityLevel);
131 const CurvBinsSpec curvBinsSpec(curvBounds.front(),
132 curvBounds.back(),
133 nCurvBins,
136 m_param_curvBounds = curvBinsSpec.constructArray();
137 }
138 }
139
140 // Construct hough tree
142 m_houghTree = std::make_unique<SimpleRLTaggedWireHitPhi0CurvHough>(maxTreeLevel, m_curlCurv);
143 m_houghTree->setSectorLevelSkip(m_param_sectorLevelSkip);
144 m_houghTree->assignArray<DiscretePhi0>(phi0BinsSpec.constructArray(), phi0BinsSpec.getNOverlap());
146 m_houghTree->initialize();
147}
148
149void AxialTrackCreatorHitHough::apply(const std::vector<const CDCWireHit*>& axialWireHits,
150 std::vector<CDCTrack>& tracks)
151{
152 // Reset the mask flag and select only the untaken hits
153 std::vector<const CDCWireHit*> unusedAxialWireHits;
154 for (const CDCWireHit* wireHit : axialWireHits) {
155 (*wireHit)->setMaskedFlag(false);
156 if ((*wireHit)->hasTakenFlag()) continue;
157 unusedAxialWireHits.push_back(wireHit);
158 }
159
160 // Setup the level processor and obtain its parameter list to be set.
161 using Node = typename SimpleRLTaggedWireHitPhi0CurvHough::Node;
163 AxialLegendreLeafProcessor<Node> leafProcessor(maxTreeLevel);
164 leafProcessor.setAxialWireHits(axialWireHits);
165 ModuleParamList moduleParamList;
166 const std::string prefix = "";
167 leafProcessor.exposeParameters(&moduleParamList, prefix);
168
169 // Find tracks with increasingly relaxed conditions in the hough grid
170 m_houghTree->seed(std::move(unusedAxialWireHits));
171 for (const ParameterVariantMap& passParameters : m_param_relaxationSchedule) {
172 AssignParameterVisitor::update(&moduleParamList, passParameters);
173 leafProcessor.beginWalk();
174 m_houghTree->findUsing(leafProcessor);
175 }
176 m_houghTree->fell();
177
178 // Write out tracks as return value
179 const std::vector<CDCTrack>& foundTracks = leafProcessor.getTracks();
180 tracks.insert(tracks.end(), foundTracks.begin(), foundTracks.end());
181}
182
184{
185 m_houghTree->raze();
186 m_houghTree.reset();
188}
189
190std::vector<float> AxialTrackCreatorHitHough::getDefaultCurvBounds(std::array<float, 2> curvSpan, int granularityLevel)
191{
192 using BinSpan = std::array<float, 2>;
193 using BinSpans = std::vector<BinSpan>;
194 std::vector<BinSpans> binSpansByLevel(granularityLevel + 1);
195 binSpansByLevel[0].push_back(BinSpan({curvSpan[0], curvSpan[1]}));
196
197 for (int level = 1; level <= granularityLevel; ++level) {
198 for (const BinSpan& binSpan : binSpansByLevel[level - 1]) {
199 const float subBinWidth = std::fabs(binSpan[1] - binSpan[0]) / 2;
200 const float middle = binSpan[0] + (binSpan[1] - binSpan[0]) / 2.0;
201
202 // Expanding bins somewhat to have a overlap
203 // Assuming granularity level = 12
204 // For level 6 to 7 only expand 1 / 4, for higher levels expand 1 / 8.
205 // Never expand for curvatures lower than 0.005
206 // (copied from the Legendre method. Works well, but some experimentation
207 // needs to be made to know why)
208 const float extension = [&]() {
209 if ((level + 7 <= granularityLevel)
210 // or (std::fabs(middle) <= 0.007)
211 or (std::fabs(middle) <= 0.005)) {
212 return 0.0;
213 } else if (level + 5 < granularityLevel) {
214 return subBinWidth / 4.0;
215 } else {
216 return subBinWidth / 8.0;
217 }
218 }();
219
220 const float lower1 = binSpan[0] - extension;
221 const float upper1 = middle + extension;
222
223 const float lower2 = middle - extension;
224 const float upper2 = binSpan[1] + extension;
225
226 binSpansByLevel[level].push_back({lower1, upper1});
227 binSpansByLevel[level].push_back({lower2, upper2});
228 }
229 }
230
231 // Return highest level as prepared bin bounds.
232 std::vector<float> result;
233
234 for (BinSpan& binSpan : binSpansByLevel[granularityLevel]) {
235 result.push_back(binSpan[0]);
236 result.push_back(binSpan[1]);
237 }
238 return result;
239}
The Module parameter list class.
Predicate class that is feed the nodes in a WeightedHoughTree walk It decides if a node should be fur...
void setAxialWireHits(std::vector< const CDCWireHit * > axialWireHits)
Set the pool of all axial wire hits to be used in the postprocessing.
void exposeParameters(ModuleParamList *moduleParamList, const std::string &prefix)
Expose the parameters as a module parameter list.
void beginWalk()
Function to notify the leaf processor about changes in parameters before a new walk.
const std::vector< CDCTrack > & getTracks() const
Getter for the tracks.
const double m_curlCurv
Curvature below which particles from IP do not leave the CDC.
static const int c_curvDivisions
Fixed parameter: Number of divisions in the curv direction.
void apply(const std::vector< const CDCWireHit * > &axialWireHits, std::vector< CDCTrack > &tracks) final
Generates the tracks from the given segments into the output argument.
std::unique_ptr< SimpleRLTaggedWireHitPhi0CurvHough > m_houghTree
The hough space tree search.
void initialize() final
Initialize the findlet before event processing.
std::vector< ParameterVariantMap > m_param_relaxationSchedule
Parameter: Relaxation schedule for the leaf processor in the hough tree.
int m_param_sectorLevelSkip
Parameter: Number of levels to be skipped in the hough space on the first level to form sectors.
std::string getDescription() final
Short description of the findlet.
int m_param_granularityLevel
Parameter: Level of divisions in the hough space.
int m_param_discretePhi0Width
Parameter: Width of the phi0 bins at the highest level of the hough space.
static std::vector< float > getDefaultCurvBounds(std::array< float, 2 > curvSpan, int granularityLevel)
Get a series of parameters to be set for each pass over the rough hough space.
std::vector< float > m_param_curvBounds
Parameter: hough bounds.
void exposeParameters(ModuleParamList *moduleParamList, const std::string &prefix) final
Expose the parameters to a module.
int m_param_discreteCurvOverlap
Parameter: Overlap of the curvature bins at the highest level of the hough space.
static const int c_phi0Divisions
Fixed parameter: Number of divisions in the phi0 direction.
void terminate() final
Cleanup the findlet after event processing.
int m_param_discreteCurvWidth
Parameter: Width of the curvature bins at the highest level of the hough space.
int m_param_discretePhi0Overlap
Parameter: Overlap of the phi0 bins at the highest level of the hough space.
Class representing a hit wire in the central drift chamber.
Definition CDCWireHit.h:55
Strategy to construct discrete curve points from discrete overlap specifications.
Definition CurvRep.h:23
DiscreteCurv::Array constructArray() const
Construct the array of discrete curve positions.
Definition CurvRep.h:40
Strategy to construct discrete phi0 points from discrete overlap specifications.
Definition Phi0Rep.h:20
DiscretePhi0::Array constructArray() const
Construct the array of discrete phi0 positions.
Definition Phi0Rep.cc:23
int getNOverlap() const
Getter for the overlap in discrete number of positions.
Definition Phi0Rep.h:47
void addParameter(const std::string &name, T &paramVariable, const std::string &description, const T &defaultValue)
Adds a new parameter to the module list.
Abstract base class for different kinds of events.
static void update(ModuleParamList *moduleParamList, const std::map< std::string, boost::variant< T... > > &valuesByName)
Transfer all the parameters from the map boost:variant values to the module parameter list.