Belle II Software development
WholeWireHitRelationFilter.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/filters/wireHitRelation/WholeWireHitRelationFilter.h>
9
10#include <tracking/trackingUtilities/eventdata/hits/CDCWireHit.h>
11
12#include <cdc/topology/CDCWireTopology.h>
13#include <cdc/topology/CDCWire.h>
14
15#include <tracking/trackingUtilities/filters/base/RelationFilter.icc.h>
16
17#include <tracking/trackingUtilities/utilities/StringManipulation.h>
18#include <tracking/trackingUtilities/utilities/Functional.h>
19
20#include <framework/core/ModuleParamList.templateDetails.h>
21
22#include <vector>
23#include <string>
24#include <cassert>
25
26using namespace Belle2;
27using namespace CDC;
28using namespace TrackFindingCDC;
29using namespace TrackingUtilities;
30
32
34 : m_param_degree(neighborhoodDegree)
35{
36}
37
39
41 const std::string& prefix)
42{
43 moduleParamList
44 ->addParameter(prefixed(prefix, "degree"),
46 "Neighbor degree which are included. 1 for primary, 2 for secondary, 3 ...",
48}
49
50void WholeWireHitRelationFilter::prepare(const std::vector<CDCWireHit*>& wireHits)
51{
52 m_preparedWires.clear();
53 m_preparedWires.reserve(wireHits.size());
54 for (const CDCWireHit* wireHit : wireHits) {
55 m_preparedWires.push_back(&wireHit->getWire());
56 }
57 m_preparedWireHitsData = wireHits.data();
58 m_preparedWireHitsSize = wireHits.size();
59}
60
62 CDCWireHit* from,
63 const std::vector<CDCWireHit*>& wireHits) const
64{
65 const int nWireNeighbors = 8 + 10 * (m_param_degree - 1);
66 std::vector<const CDCWire*> m_wireNeighbors;
67 m_wireNeighbors.reserve(nWireNeighbors);
68
69 std::vector<CDCWireHit*> m_wireHitNeighbors;
70 m_wireHitNeighbors.reserve(2 * nWireNeighbors);
71
72 const CDCWireTopology& wireTopology = CDCWireTopology::getInstance();
73 const CDCWire& wire = from->getWire();
74
75 const CDCWire* ccwSixthSecondWireNeighbor = wireTopology.getSecondNeighborSixOClock(wire);
76 const CDCWire* ccwInWireNeighbor = wireTopology.getNeighborCCWInwards(wire);
77 const CDCWire* ccwWireNeighbor = wireTopology.getNeighborCCW(wire);
78 const CDCWire* ccwOutWireNeighbor = wireTopology.getNeighborCCWOutwards(wire);
79 const CDCWire* ccwTwelvethSecondWireNeighbor = wireTopology.getSecondNeighborTwelveOClock(wire);
80
81 const CDCWire* cwSixthSecondWireNeighbor = ccwSixthSecondWireNeighbor;
82 const CDCWire* cwInWireNeighbor = wireTopology.getNeighborCWInwards(wire);
83 const CDCWire* cwWireNeighbor = wireTopology.getNeighborCW(wire);
84 const CDCWire* cwOutWireNeighbor = wireTopology.getNeighborCWOutwards(wire);
85 const CDCWire* cwTwelvethSecondWireNeighbor = ccwTwelvethSecondWireNeighbor;
86
87 // Insert the neighbors such that they are most likely sorted.
88
89 // Degree 1 neighborhood - only add the six o'clock and the twelve o'clock neighbor once
90 if (m_param_degree > 1 and ccwSixthSecondWireNeighbor)
91 m_wireNeighbors.push_back(ccwSixthSecondWireNeighbor);
92
93 if (cwInWireNeighbor) m_wireNeighbors.push_back(cwInWireNeighbor);
94 if (ccwInWireNeighbor) m_wireNeighbors.push_back(ccwInWireNeighbor);
95
96 // cppcheck-suppress knownConditionTrueFalse ; defensive null check on the wire neighbour lookup
97 if (cwWireNeighbor) m_wireNeighbors.push_back(cwWireNeighbor);
98 // cppcheck-suppress knownConditionTrueFalse ; defensive null check on the wire neighbour lookup
99 if (ccwWireNeighbor) m_wireNeighbors.push_back(ccwWireNeighbor);
100
101 if (cwOutWireNeighbor) m_wireNeighbors.push_back(cwOutWireNeighbor);
102 if (ccwOutWireNeighbor) m_wireNeighbors.push_back(ccwOutWireNeighbor);
103
104 if (m_param_degree > 1 and ccwTwelvethSecondWireNeighbor)
105 m_wireNeighbors.push_back(ccwTwelvethSecondWireNeighbor);
106
107 for (int degree = 1; degree < m_param_degree; ++degree) {
108 if (cwSixthSecondWireNeighbor) {
109 cwSixthSecondWireNeighbor = cwSixthSecondWireNeighbor->getNeighborCW();
110 m_wireNeighbors.push_back(cwSixthSecondWireNeighbor);
111 }
112 if (ccwSixthSecondWireNeighbor) {
113 ccwSixthSecondWireNeighbor = ccwSixthSecondWireNeighbor->getNeighborCCW();
114 m_wireNeighbors.push_back(ccwSixthSecondWireNeighbor);
115 }
116
117 if (cwInWireNeighbor) {
118 cwInWireNeighbor = cwInWireNeighbor->getNeighborCW();
119 m_wireNeighbors.push_back(cwInWireNeighbor);
120 }
121 if (ccwInWireNeighbor) {
122 ccwInWireNeighbor = ccwInWireNeighbor->getNeighborCCW();
123 m_wireNeighbors.push_back(ccwInWireNeighbor);
124 }
125
126 if (cwWireNeighbor) {
127 cwWireNeighbor = cwWireNeighbor->getNeighborCW();
128 m_wireNeighbors.push_back(cwWireNeighbor);
129 }
130 if (ccwWireNeighbor) {
131 ccwWireNeighbor = ccwWireNeighbor->getNeighborCCW();
132 m_wireNeighbors.push_back(ccwWireNeighbor);
133 }
134
135 if (cwOutWireNeighbor) {
136 cwOutWireNeighbor = cwOutWireNeighbor->getNeighborCW();
137 m_wireNeighbors.push_back(cwOutWireNeighbor);
138 }
139 if (ccwOutWireNeighbor) {
140 ccwOutWireNeighbor = ccwOutWireNeighbor->getNeighborCCW();
141 m_wireNeighbors.push_back(ccwOutWireNeighbor);
142 }
143
144 if (cwTwelvethSecondWireNeighbor) {
145 cwTwelvethSecondWireNeighbor = cwTwelvethSecondWireNeighbor->getNeighborCW();
146 m_wireNeighbors.push_back(cwTwelvethSecondWireNeighbor);
147 }
148 if (ccwTwelvethSecondWireNeighbor) {
149 ccwTwelvethSecondWireNeighbor = ccwTwelvethSecondWireNeighbor->getNeighborCCW();
150 m_wireNeighbors.push_back(ccwTwelvethSecondWireNeighbor);
151 }
152 }
153
154 std::sort(std::begin(m_wireNeighbors), std::end(m_wireNeighbors));
155
156 // Use the wires precomputed by prepare() when called with the prepared vector.
157 // The comparison LessOf<Deref>() used below resolves to operator<(CDCWireHit, CDCWire),
158 // which compares the *address* of the wire of the hit with the address of the wire.
159 // Searching the precomputed wire addresses therefore evaluates exactly the same
160 // predicate on exactly the same values, only without dereferencing the wire hits.
161 const bool prepared =
162 wireHits.data() == m_preparedWireHitsData and wireHits.size() == m_preparedWireHitsSize;
163
164 for (const CDCWire* neighborWire : m_wireNeighbors) {
165 ConstVectorRange<CDCWireHit*> neighborWireHits = [&]() -> ConstVectorRange<CDCWireHit*> {
166 if (prepared)
167 {
168 const auto itRange =
169 std::equal_range(m_preparedWires.begin(), m_preparedWires.end(), neighborWire);
170 return {
171 wireHits.begin() + (itRange.first - m_preparedWires.begin()),
172 wireHits.begin() + (itRange.second - m_preparedWires.begin())};
173 }
174 return ConstVectorRange<CDCWireHit*>{
175 std::equal_range(wireHits.begin(), wireHits.end(), neighborWire, LessOf<Deref>())
176 };
177 }();
178
179 m_wireHitNeighbors.insert(m_wireHitNeighbors.end(),
180 neighborWireHits.begin(),
181 neighborWireHits.end());
182 }
183
184 return m_wireHitNeighbors;
185}
Class representing the sense wire arrangement in the whole of the central drift chamber.
TrackingUtilities::MayBePtr< const CDCWire > getNeighborCCW(const WireID &wireID) const
Getter for the nearest counterclockwise neighbor.
TrackingUtilities::MayBePtr< const CDCWire > getSecondNeighborSixOClock(const WireID &wireID) const
Getter for secondary neighbor at the six o'clock position.
TrackingUtilities::MayBePtr< const CDCWire > getNeighborCW(const WireID &wireID) const
Getter for the nearest clockwise neighbor.
static CDCWireTopology & getInstance()
Getter for the singleton instance of the wire topology.
TrackingUtilities::MayBePtr< const CDCWire > getNeighborCWOutwards(const WireID &wireID) const
Getter for the nearest clockwise neighbor in the next layer outwards.
TrackingUtilities::MayBePtr< const CDCWire > getNeighborCCWInwards(const WireID &wireID) const
Getter for the nearest counterclockwise neighbor in the next layer outwards.
TrackingUtilities::MayBePtr< const CDCWire > getNeighborCCWOutwards(const WireID &wireID) const
Getter for the nearest counterclockwise neighbor in the next layer outwards.
TrackingUtilities::MayBePtr< const CDCWire > getSecondNeighborTwelveOClock(const WireID &wireID) const
Getter for secondary neighbor at the twelve o'clock position.
TrackingUtilities::MayBePtr< const CDCWire > getNeighborCWInwards(const WireID &wireID) const
Getter for the nearest clockwise neighbor in the next layer outwards.
Class representing a sense wire in the central drift chamber.
Definition CDCWire.h:50
TrackingUtilities::MayBePtr< const CDCWire > getNeighborCCW() const
Gives the closest neighbor in the counterclockwise direction - always exists.
Definition CDCWire.cc:159
TrackingUtilities::MayBePtr< const CDCWire > getNeighborCW() const
Gives the closest neighbor in the clockwise direction - always exists.
Definition CDCWire.cc:164
The Module parameter list class.
void prepare(const std::vector< TrackingUtilities::CDCWireHit * > &wireHits)
Precompute the wires of the given wire hits to speed up the searches in the following getPossibleTos ...
WholeWireHitRelationFilter(int neighborhoodDegree=2)
Constructor form the default neighborhood degree.
TrackingUtilities::CDCWireHit *const * m_preparedWireHitsData
Data pointer of the prepared wire hit vector used to recognize it in getPossibleTos.
~WholeWireHitRelationFilter() override
Default destructor.
std::vector< TrackingUtilities::CDCWireHit * > getPossibleTos(TrackingUtilities::CDCWireHit *from, const std::vector< TrackingUtilities::CDCWireHit * > &wireHits) const final
Returns a vector containing the neighboring wire hits of the given wire hit out of the sorted range g...
void exposeParameters(ModuleParamList *moduleParamList, const std::string &prefix) final
Expose the parameters to a module.
std::vector< const CDC::CDCWire * > m_preparedWires
Memory for the wires of the prepared wire hit vector.
std::size_t m_preparedWireHitsSize
Size of the prepared wire hit vector used to recognize it in getPossibleTos.
Class representing a hit wire in the central drift chamber.
Definition CDCWireHit.h:56
Iterator begin() const
Begin of the range for range based for.
Definition Range.h:64
Iterator end() const
End of the range for range based for.
Definition Range.h:68
Base class for filtering the neighborhood of objects.
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.