82 const std::vector<CDCWireHit*>& wireHits)
const
92 auto findWireHitRange = [&](
const CDCWire * neighborWire) -> ConstVectorRange<CDCWireHit*> {
100 return ConstVectorRange<CDCWireHit*>{
101 std::equal_range(wireHits.begin(), wireHits.end(), neighborWire, LessOf<Deref>())
107 std::array<std::pair<const CDCWire*, int>, 12> wireNeighbors;
108 int nWireNeighbors = 0;
110 std::vector<CDCWireHit*> wireHitNeighbors;
111 wireHitNeighbors.reserve(12);
113 std::array<short, 12> missingPrimaryNeighbor = {0};
117 const CDCWire& wire = from->getWire();
120 for (
short oClockDirection : {5, 7, 3, 9, 1, 11}) {
121 MayBePtr<const CDCWire> neighborWire = wireTopology.
getPrimaryNeighbor(oClockDirection, wire);
122 if (neighborWire) wireNeighbors[nWireNeighbors++] = {neighborWire, oClockDirection};
125 std::sort(wireNeighbors.begin(), wireNeighbors.begin() + nWireNeighbors);
127 for (std::pair<const CDCWire*, int> wireAndOClockDirection :
128 asRange(wireNeighbors.begin(), wireNeighbors.begin() + nWireNeighbors)) {
129 const CDCWire* neighborWire = wireAndOClockDirection.first;
131 int oClockDirection = wireAndOClockDirection.second;
133 ConstVectorRange<CDCWireHit*> wireHitRange = findWireHitRange(neighborWire);
134 if (wireHitRange.
empty()) {
135 int ccwOClockDirection = oClockDirection - 1;
136 int cwOClockDirection = oClockDirection == 11 ? 0 : oClockDirection + 1;
137 ++missingPrimaryNeighbor[ccwOClockDirection];
138 ++missingPrimaryNeighbor[oClockDirection];
139 ++missingPrimaryNeighbor[cwOClockDirection];
141 wireHitNeighbors.insert(wireHitNeighbors.end(), wireHitRange.
begin(), wireHitRange.
end());
144 size_t nPrimaryWireHitNeighbors = wireHitNeighbors.size();
149 MayBePtr<const CDCWire> neighborWire = wireTopology.
getSecondaryNeighbor(oClockDirection, wire);
150 if (not neighborWire)
continue;
151 if (missingPrimaryNeighbor[oClockDirection] <
154 wireNeighbors[nWireNeighbors++] = {neighborWire, oClockDirection};
157 std::sort(wireNeighbors.begin(), wireNeighbors.begin() + nWireNeighbors);
159 for (std::pair<const CDCWire*, int> wireAndOClockDirection :
160 asRange(wireNeighbors.begin(), wireNeighbors.begin() + nWireNeighbors)) {
161 const CDCWire* neighborWire = wireAndOClockDirection.first;
162 ConstVectorRange<CDCWireHit*> wireHitRange = findWireHitRange(neighborWire);
163 wireHitNeighbors.insert(wireHitNeighbors.end(), wireHitRange.
begin(), wireHitRange.
end());
167 std::inplace_merge(wireHitNeighbors.begin(),
168 wireHitNeighbors.begin() + nPrimaryWireHitNeighbors,
169 wireHitNeighbors.end(),
170 std::less<CDCWireHit*>());
172 return wireHitNeighbors;