44 double referenceTicks,
49 firstWire = hitVec.front()->getHits()[planeToCheck]->WireID().Wire;
50 lastWire = hitVec.back()->getHits()[planeToCheck]->WireID().Wire;
52 double maxDeltaTicks = referenceTicks - hitVec.front()->getHits()[planeToCheck]->getTimeTicks();
53 double minDeltaTicks = referenceTicks - hitVec.back()->getHits()[planeToCheck]->getTimeTicks();
55 if (minDeltaTicks > maxDeltaTicks) std::swap(maxDeltaTicks, minDeltaTicks);
57 double bestDeltaTicks = 1000000.;
60 if (hitVec.size() > 1) {
66 double nextBestDeltaTicks = bestDeltaTicks;
68 for (
const auto& hitPair : hitVec) {
69 int curWire = hitPair->getHits()[planeToCheck]->WireID().Wire;
70 double deltaTicks = referenceTicks - hitPair->getHits()[planeToCheck]->getTimeTicks();
72 maxDeltaTicks = std::max(maxDeltaTicks, deltaTicks);
73 minDeltaTicks = std::min(minDeltaTicks, deltaTicks);
75 if (bestDeltaTicks > fabs(deltaTicks)) {
77 nextBestDeltaTicks = bestDeltaTicks;
78 bestDeltaTicks = fabs(deltaTicks);
80 else if (nextBestDeltaTicks > fabs(deltaTicks)) {
81 nextBestDeltaTicks = fabs(deltaTicks);
86 if (fabs(curWire - lastWire) > 2000) {
87 if (referenceWire <= lastWire)
break;
91 maxDeltaTicks = deltaTicks;
92 minDeltaTicks = deltaTicks;
93 bestDeltaTicks = fabs(deltaTicks);
94 nextBestDeltaTicks = bestDeltaTicks;
100 bestDeltaTicks = nextBestDeltaTicks;
105 if (minDeltaTicks * maxDeltaTicks > 0. && bestDeltaTicks > 30.) bestDeltaTicks = 0.;
107 return bestDeltaTicks;
116 for (
const auto leftHit : left->
getHits()) {
117 if (leftHit->WireID().Plane == m_plane) {
118 for (
const auto rightHit : right->
getHits()) {
119 if (rightHit->WireID().Plane == m_plane) {
120 return leftHit->WireID().Wire < rightHit->WireID().Wire;
136 return left.second < right.second;
146 typedef std::map<const reco::ClusterHit2D*, std::vector<const reco::ClusterHit3D*>>
149 Hit2DtoHit3DMapU hit2DToHit3DMap[3];
151 for (
const auto& hitPair : hitPairList) {
156 unsigned status = hitPair->getStatusBits();
158 if ((status & 0x7) != 0x7)
continue;
160 for (
const auto& hit2D : hitPair->getHits()) {
161 size_t plane = hit2D->WireID().Plane;
163 hit2DToHit3DMap[plane][hit2D].push_back(hitPair);
168 for (
size_t idx = 0; idx < 3; idx++) {
169 for (
auto& mapPair : hit2DToHit3DMap[idx]) {
170 size_t numHitPairs = mapPair.second.size();
171 int planeToCheck = (idx + 1) % 3;
174 std::sort(mapPair.second.begin(), mapPair.second.end(),
OrderHitsAlongWire(planeToCheck));
179 int nSkeletonPoints(0);
182 for (
const auto& hitPair : hitPairList) {
187 if ((hitPair->getStatusBits() & 0x7) != 7)
continue;
201 size_t numHitPairs[3] = {
203 int deltaWires[3] = {0, 0, 0};
204 double planeDeltaT[3] = {0., 0., 0.};
205 double bestDeltaTicks[3] = {0., 0., 0.};
206 int wireNumByPlane[3] = {int(hitPair->getHits()[0]->WireID().Wire),
207 int(hitPair->getHits()[1]->WireID().Wire),
208 int(hitPair->getHits()[2]->WireID().Wire)};
210 size_t bestPlaneIdx(0);
213 for (
size_t planeIdx = 0; planeIdx < 3; planeIdx++) {
217 std::vector<const reco::ClusterHit3D*>& hitVec(hit2DToHit3DMap[planeIdx][hit2D]);
219 numHitPairs[planeIdx] = hitVec.size();
221 if (numHitPairs[planeIdx] > 1) {
222 int planeToCheck = (planeIdx + 1) % 3;
228 wireNumByPlane[planeToCheck],
233 int deltaFirst = wireNumByPlane[planeToCheck] - firstWire;
234 int deltaLast = wireNumByPlane[planeToCheck] - lastWire;
239 deltaWires[planeIdx] = deltaFirst + deltaLast;
240 numHitPairs[planeIdx] = lastWire - firstWire + 1;
241 planeDeltaT[planeIdx] =
242 fabs(hit2DTimeTicks - hitPair->getHits()[planeToCheck]->getTimeTicks());
248 if (numHitPairs[planeIdx] < numHitPairs[bestPlaneIdx]) { bestPlaneIdx = planeIdx; }
252 if (bestPlaneIdx < 3 && numHitPairs[bestPlaneIdx] > 0) {
254 int maxBestWires = 0.05 * numHitPairs[bestPlaneIdx] + 1;
259 if (fabs(deltaWires[bestPlaneIdx]) < maxBestWires + 1) {
270 int nextBestIdx = (bestPlaneIdx + 1) % 3;
272 for (
size_t idx = 0; idx < 3; idx++) {
273 if (idx == bestPlaneIdx)
continue;
275 if (numHitPairs[idx] < numHitPairs[nextBestIdx]) nextBestIdx = idx;
278 if (nextBestIdx > 2) {
279 std::cout <<
"***** invalid next best plane: " << nextBestIdx <<
" *******" 284 if (planeDeltaT[bestPlaneIdx] < 1.01 * bestDeltaTicks[bestPlaneIdx] &&
285 planeDeltaT[nextBestIdx] < 6.01 * bestDeltaTicks[nextBestIdx])
297 return nSkeletonPoints;
303 for (
const auto& hit3D : inputHitList)
315 typedef std::map<const reco::ClusterHit2D*, std::vector<const reco::ClusterHit3D*>>
319 Hit2DtoHit3DMap hit2DToHit3DMap[3];
322 unsigned int nSkeletonHits(0);
325 for (
const auto& hitPair : skeletonHitList) {
332 for (
const auto& hit2D : hitPair->getHits()) {
333 size_t plane = hit2D->WireID().Plane;
335 hit2DToHit3DMap[plane][hit2D].push_back(hitPair);
340 if (!nSkeletonHits)
return;
344 for (
size_t idx = 0; idx < 3; idx++) {
345 for (
auto& mapPair : hit2DToHit3DMap[idx]) {
346 size_t numHitPairs = mapPair.second.size();
347 int planeToCheck = (idx + 1) % 3;
350 std::sort(mapPair.second.begin(), mapPair.second.end(),
OrderHitsAlongWire(planeToCheck));
363 for (
int bestPlaneVecIdx = 0; bestPlaneVecIdx < 2; bestPlaneVecIdx++) {
364 std::list<reco::ClusterHit3D> tempHitPairList;
367 std::map<const reco::ClusterHit3D*, const reco::ClusterHit3D*> hit3DToHit3DMap;
369 while (hitPairItr != skeletonHitList.end()) {
372 std::vector<std::pair<size_t, size_t>> bestPlaneVec;
374 for (
const auto& hit2D : hit3D->
getHits()) {
375 bestPlaneVec.push_back(std::pair<size_t, size_t>(
376 hit2D->WireID().Plane, hit2DToHit3DMap[hit2D->WireID().Plane][hit2D].size()));
379 std::sort(bestPlaneVec.begin(), bestPlaneVec.end(),
OrderBestPlanes());
381 size_t bestPlaneIdx = bestPlaneVec[bestPlaneVecIdx].first;
382 size_t bestPlaneCnt = bestPlaneVec[bestPlaneVecIdx].second;
384 if (bestPlaneCnt > 5)
continue;
386 std::vector<const reco::ClusterHit3D*>& hit3DVec =
387 hit2DToHit3DMap[bestPlaneIdx][hit3D->
getHits()[bestPlaneIdx]];
389 Eigen::Vector3f avePosition(hit3D->
getPosition()[0], 0., 0.);
391 for (
const auto& tempHit3D : hit3DVec) {
392 avePosition[1] += tempHit3D->getPosition()[1];
393 avePosition[2] += tempHit3D->getPosition()[2];
396 avePosition[1] *= 1. / double(hit3DVec.size());
397 avePosition[2] *= 1. / double(hit3DVec.size());
415 tempHitPairListPtr.push_back(&tempHitPairList.back());
417 hit3DToHit3DMap[tempHitPairListPtr.back()] = hit3D;
420 for (
const auto& pair : hit3DToHit3DMap) {
421 pair.second->
setPosition(pair.first->getPosition());
constexpr auto const & right(const_AssnsIter< L, R, D, Dir > const &a, const_AssnsIter< L, R, D, Dir > const &b)
float getTimeTicks() const
const Eigen::Vector3f getPosition() const
const std::vector< float > getHitDelTSigVec() const
float getTotalCharge() const
Hit has been rejected for any reason.
float getSigmaPeakTime() const
float getOverlapFraction() const
unsigned int getStatusBits() const
void GetSkeletonHits(const reco::HitPairListPtr &inputHitList, reco::HitPairListPtr &skeletonHitList) const
Return the skeleton hits from the input list.
float getDocaToAxis() const
SkeletonAlg(fhicl::ParameterSet const &pset)
Constructor.
void reconfigure(fhicl::ParameterSet const &pset)
a handler for the case where the algorithm control parameters are to be reset
OrderHitsAlongWire(int plane=0)
float getAvePeakTime() const
float getChargeAsymmetry() const
int FindMedialSkeleton(reco::HitPairListPtr &hitPairList) const
This is intended to find the medial skeleton given a list of input hit pairs.
T get(std::string const &key) const
double m_minimumDeltaTicks
void AverageSkeletonPositions(reco::HitPairListPtr &skeletonHitList) const
Modifies the position of input skeleton hits by averaging along the "best" wire direction.
std::list< const reco::ClusterHit3D * > HitPairListPtr
bool operator()(const reco::ClusterHit3D *left, const reco::ClusterHit3D *right)
Definition of data types for geometry description.
constexpr auto const & left(const_AssnsIter< L, R, D, Dir > const &a, const_AssnsIter< L, R, D, Dir > const &b)
double m_maximumDeltaTicks
double FindFirstAndLastWires(std::vector< const reco::ClusterHit3D * > &hitVec, int planeToCheck, int referenceWire, double referenceTicks, int &firstWire, int &lastWire) const
A function to find the bounding wires in a given view.
bool operator()(const std::pair< size_t, size_t > &left, const std::pair< size_t, size_t > &right)
Header file to define the interface to the SkeletonAlg.
~SkeletonAlg()
Destructor.
const std::vector< geo::WireID > & getWireIDs() const
float getArclenToPoca() const
float getDeltaPeakTime() const
Skeleton hit position averaged.
float getHitChiSquare() const
const ClusterHit2DVec & getHits() const
void setPosition(const Eigen::Vector3f &pos) const