LArSoft  v09_90_00
Liquid Argon Software toolkit - https://larsoft.org/
pma::PMAlgVertexing Class Reference

#include "PMAlgVertexing.h"

Classes

struct  Config
 

Public Member Functions

 PMAlgVertexing (const Config &config)
 
 PMAlgVertexing (const fhicl::ParameterSet &pset)
 
 ~PMAlgVertexing ()
 
void reset ()
 
size_t run (const detinfo::DetectorPropertiesData &detProp, pma::TrkCandidateColl &trk_input)
 
size_t run (pma::TrkCandidateColl &trk_input, const std::vector< TVector3 > &vtx_input)
 
std::vector< std::pair< TVector3, std::vector< std::pair< size_t, bool > > > > getVertices (const pma::TrkCandidateColl &tracks, bool onlyBranching=false) const
 
std::vector< std::pair< TVector3, size_t > > getKinks (const pma::TrkCandidateColl &tracks) const
 

Private Member Functions

bool has (const std::vector< size_t > &v, size_t idx) const
 
std::vector< pma::VtxCandidatefirstPassCandidates () const
 
std::vector< pma::VtxCandidatesecondPassCandidates () const
 
size_t makeVertices (detinfo::DetectorPropertiesData const &detProp, std::vector< pma::VtxCandidate > &candidates)
 
std::vector< std::pair< double, double > > getdQdx (const pma::Track3D &trk) const
 Get dQ/dx sequence to detect various features. More...
 
double convolute (size_t idx, size_t len, double *adc, double const *shape) const
 Get convolution value. More...
 
bool isSingleParticle (pma::Track3D *trk1, pma::Track3D *trk2) const
 Check if colinear in 3D and dQ/dx with no significant step. More...
 
void mergeBrokenTracks (pma::TrkCandidateColl &trk_input) const
 
void splitMergedTracks (pma::TrkCandidateColl &trk_input) const
 Split track and add vertex and reoptimize when dQ/dx step detected. More...
 
void findKinksOnTracks (const detinfo::DetectorPropertiesData &detProp, pma::TrkCandidateColl &trk_input) const
 Remove penalty on the angle if kink detected and reopt track. More...
 
void cleanTracks ()
 
void sortTracks (const pma::TrkCandidateColl &trk_input)
 
void collectTracks (pma::TrkCandidateColl &result)
 

Private Attributes

pma::TrkCandidateColl fOutTracks
 
pma::TrkCandidateColl fShortTracks
 
pma::TrkCandidateColl fEmTracks
 
pma::TrkCandidateColl fExcludedTracks
 
double fMinTrackLength
 
bool fFindKinks
 
double fKinkMinDeg
 
double fKinkMinStd
 

Detailed Description

Definition at line 36 of file PMAlgVertexing.h.

Constructor & Destructor Documentation

pma::PMAlgVertexing::PMAlgVertexing ( const Config config)
pma::PMAlgVertexing::PMAlgVertexing ( const fhicl::ParameterSet pset)
inline

Definition at line 58 of file PMAlgVertexing.h.

59  {}
PMAlgVertexing(const Config &config)
pma::PMAlgVertexing::~PMAlgVertexing ( )

Definition at line 25 of file PMAlgVertexing.cxx.

References cleanTracks().

26 {
27  cleanTracks();
28 }

Member Function Documentation

void pma::PMAlgVertexing::cleanTracks ( )
private

Definition at line 31 of file PMAlgVertexing.cxx.

References pma::TrkCandidateColl::clear(), fEmTracks, fExcludedTracks, fOutTracks, fShortTracks, and pma::TrkCandidateColl::tracks().

Referenced by sortTracks(), and ~PMAlgVertexing().

32 {
33  for (auto& t : fOutTracks.tracks())
34  t.DeleteTrack();
35  fOutTracks.clear();
36 
37  for (auto& t : fShortTracks.tracks())
38  t.DeleteTrack();
40 
41  for (auto& t : fEmTracks.tracks())
42  t.DeleteTrack();
43  fEmTracks.clear();
44 
45  for (auto& t : fExcludedTracks.tracks())
46  t.DeleteTrack();
48 }
pma::TrkCandidateColl fEmTracks
pma::TrkCandidateColl fShortTracks
pma::TrkCandidateColl fOutTracks
pma::TrkCandidateColl fExcludedTracks
std::vector< TrkCandidate > const & tracks() const
void pma::PMAlgVertexing::collectTracks ( pma::TrkCandidateColl result)
private

Definition at line 51 of file PMAlgVertexing.cxx.

References pma::TrkCandidateColl::clear(), fEmTracks, fExcludedTracks, fOutTracks, fShortTracks, pma::TrkCandidateColl::push_back(), pma::TrkCandidateColl::size(), and pma::TrkCandidateColl::tracks().

Referenced by run().

52 {
53  mf::LogVerbatim("pma::PMAlgVertexing") << "clean input: " << result.size() << std::endl;
54  for (auto& t : result.tracks())
55  t.DeleteTrack();
56  result.clear();
57 
58  mf::LogVerbatim("pma::PMAlgVertexing")
59  << "fill input from out: " << fOutTracks.size() << std::endl;
60  for (auto const& t : fOutTracks.tracks())
61  result.push_back(t);
62  fOutTracks.clear();
63 
64  mf::LogVerbatim("pma::PMAlgVertexing")
65  << "fill input from short: " << fShortTracks.size() << std::endl;
66  for (auto const& t : fShortTracks.tracks())
67  result.push_back(t);
69 
70  mf::LogVerbatim("pma::PMAlgVertexing") << "fill input from em: " << fEmTracks.size() << std::endl;
71  for (auto const& t : fEmTracks.tracks())
72  result.push_back(t);
73  fEmTracks.clear();
74 
75  mf::LogVerbatim("pma::PMAlgVertexing")
76  << "copy back excluded tracks: " << fExcludedTracks.size() << std::endl;
77  for (auto const& t : fExcludedTracks.tracks())
78  result.push_back(t);
80 }
pma::TrkCandidateColl fEmTracks
MaybeLogger_< ELseverityLevel::ELsev_info, true > LogVerbatim
size_t size() const
pma::TrkCandidateColl fShortTracks
pma::TrkCandidateColl fOutTracks
pma::TrkCandidateColl fExcludedTracks
void push_back(const TrkCandidate &trk)
std::vector< TrkCandidate > const & tracks() const
double pma::PMAlgVertexing::convolute ( size_t  idx,
size_t  len,
double *  adc,
double const *  shape 
) const
private

Get convolution value.

Definition at line 381 of file PMAlgVertexing.cxx.

References pmtana::mean(), and sum.

Referenced by isSingleParticle().

385 {
386  size_t half = len >> 1;
387  double v, mean = 0.0, stdev = 0.0;
388  for (size_t i = 0; i < len; i++) {
389  v = adc[idx - half + i];
390  mean += v;
391  stdev += v * v;
392  }
393  mean /= len;
394  stdev /= len;
395  stdev -= mean;
396 
397  double sum = 0.0;
398  for (size_t i = 0; i < len; i++)
399  sum += (adc[idx - half + i] - mean) * shape[i];
400 
401  return sum / sqrt(stdev);
402 }
double mean(const std::vector< short > &wf, size_t start, size_t nsample)
Definition: UtilFunc.cxx:13
Double_t sum
Definition: plot.C:31
void pma::PMAlgVertexing::findKinksOnTracks ( const detinfo::DetectorPropertiesData detProp,
pma::TrkCandidateColl trk_input 
) const
private

Remove penalty on the angle if kink detected and reopt track.

Definition at line 532 of file PMAlgVertexing.cxx.

References e, fKinkMinDeg, fKinkMinStd, has(), pmtana::mean(), n, pma::Track3D::Nodes(), pma::Track3D::Optimize(), and pma::TrkCandidateColl::size().

Referenced by run().

534 {
535  if (trk_input.size() < 1) return;
536 
537  mf::LogVerbatim("pma::PMAlgVertexing")
538  << "Find kinks on tracks, reopt with no penalty on angle where kinks.";
539  for (size_t t = 0; t < trk_input.size(); ++t) {
540  pma::Track3D* trk = trk_input[t].Track();
541  if (trk->Nodes().size() < 5) continue;
542 
543  trk->Optimize(detProp, 0, 1.0e-5, false);
544 
545  std::vector<size_t> tested_nodes;
546  bool kinkFound = true;
547  while (kinkFound) {
548  int kinkIdx = -1, nnodes = 0;
549  double mean = 0.0, stdev = 0.0, min = 1.0, max_a = 0.0;
550  for (size_t n = 1; n < trk->Nodes().size() - 1; ++n) {
551  auto const& node = *(trk->Nodes()[n]);
552 
553  if (node.IsVertex() || node.IsTPCEdge()) continue;
554  nnodes++;
555 
556  double c = -node.SegmentCosTransverse();
557  double a = 180.0 * (1 - std::acos(node.SegmentCosTransverse()) / TMath::Pi());
558  mean += c;
559  stdev += c * c;
560  if ((c < min) && !has(tested_nodes, n)) {
561  if ((n > 1) && (n < trk->Nodes().size() - 2)) kinkIdx = n;
562  min = c;
563  max_a = a;
564  }
565  }
566 
567  kinkFound = false;
568  if ((nnodes > 2) && (kinkIdx > 0) && (max_a > fKinkMinDeg)) {
569  mean /= nnodes;
570  stdev /= nnodes;
571  stdev -= mean * mean;
572 
573  double thr = 1.0 - fKinkMinStd * stdev;
574  if (min < thr) {
575  mf::LogVerbatim("pma::PMAlgVertexing") << " kink a: " << max_a << "deg";
576  trk->Nodes()[kinkIdx]->SetVertex(true);
577  tested_nodes.push_back(kinkIdx);
578  kinkFound = true;
579 
580  trk->Optimize(detProp, 0, 1.0e-5, false, false);
581  double c = -trk->Nodes()[kinkIdx]->SegmentCosTransverse();
582  double a =
583  180.0 * (1 - std::acos(trk->Nodes()[kinkIdx]->SegmentCosTransverse()) / TMath::Pi());
584 
585  if ((a <= fKinkMinDeg) || (c >= thr)) // not a significant kink after precise optimization
586  {
587  mf::LogVerbatim("pma::PMAlgVertexing") << " -> tag removed after reopt";
588  trk->Nodes()[kinkIdx]->SetVertex(
589  false); // kinkIdx is saved in tested_nodes to avoid inf loop
590  }
591  }
592  }
593  }
594 
595  mf::LogVerbatim("pma::PMAlgVertexing") << "-------- done --------";
596  }
597 }
MaybeLogger_< ELseverityLevel::ELsev_info, true > LogVerbatim
size_t size() const
double Optimize(const detinfo::DetectorPropertiesData &detProp, int nNodes=-1, double eps=0.01, bool selAllHits=true, bool setAllNodes=true, size_t selSegHits=0, size_t selVtxHits=0)
Main optimization method.
double mean(const std::vector< short > &wf, size_t start, size_t nsample)
Definition: UtilFunc.cxx:13
Char_t n[5]
std::vector< pma::Node3D * > const & Nodes() const noexcept
Definition: PmaTrack3D.h:274
Float_t e
Definition: plot.C:35
bool has(const std::vector< size_t > &v, size_t idx) const
std::vector< pma::VtxCandidate > pma::PMAlgVertexing::firstPassCandidates ( ) const
private

Definition at line 123 of file PMAlgVertexing.cxx.

References pma::VtxCandidate::Add(), fOutTracks, pma::VtxCandidate::Mse(), and pma::TrkCandidateColl::size().

Referenced by run().

124 {
125  std::vector<pma::VtxCandidate> candidates;
126  for (size_t t = 0; t < fOutTracks.size() - 1; t++) {
127  for (size_t u = t + 1; u < fOutTracks.size(); u++) {
128  pma::VtxCandidate candidate;
129  if (!candidate.Add(fOutTracks[t])) break; // no segments with length > thr
130 
131  // **************************** try Mse2D / or only Mse ************************************
132  if (candidate.Add(fOutTracks[u]) && (sqrt(candidate.Mse()) < 1.0))
133  //if (candidate.Add(fOutTracks[u]) && (sqrt(candidate.Mse()) < 2.0) && (candidate.Mse2D() < 1.0))
134  {
135  candidates.push_back(candidate);
136  }
137  }
138  }
139  return candidates;
140 }
size_t size() const
double Mse() const
pma::TrkCandidateColl fOutTracks
bool Add(const pma::TrkCandidate &trk)
std::vector< std::pair< double, double > > pma::PMAlgVertexing::getdQdx ( const pma::Track3D trk) const
private

Get dQ/dx sequence to detect various features.

Definition at line 341 of file PMAlgVertexing.cxx.

References pma::Track3D::GetRawdEdxSequence(), geo::kU, geo::kV, geo::kZ, pma::Track3D::NHits(), and pma::Track3D::size().

Referenced by isSingleParticle().

342 {
343  std::vector<std::pair<double, double>> result;
344 
345  unsigned int view = geo::kZ;
346  unsigned int nhits = trk.NHits(view);
347  unsigned int max = nhits;
348 
349  nhits = trk.NHits(geo::kV);
350  if (nhits > max) {
351  max = nhits;
352  view = geo::kV;
353  }
354 
355  nhits = trk.NHits(geo::kU);
356  if (nhits > max) {
357  max = nhits;
358  view = geo::kU;
359  }
360 
361  if (max >= 16) {
362  std::map<size_t, std::vector<double>> dqdx;
363  trk.GetRawdEdxSequence(dqdx, view);
364 
365  for (size_t i = 0; i < trk.size(); i++) {
366  auto it = dqdx.find(i);
367  if (it != dqdx.end()) {
368  if (it->second[6] > 0.0) // dx > 0
369  {
370  double dvalue = it->second[5] / it->second[6];
371  result.emplace_back(std::pair<double, double>(dvalue, it->second[7]));
372  }
373  }
374  }
375  }
376 
377  return result;
378 }
Planes which measure V.
Definition: geo_types.h:136
Planes which measure Z direction.
Definition: geo_types.h:138
Planes which measure U.
Definition: geo_types.h:135
unsigned int NHits(unsigned int view) const
Definition: PmaTrack3D.cxx:421
double GetRawdEdxSequence(std::map< size_t, std::vector< double >> &dedx, unsigned int view=geo::kZ, unsigned int skip=0, bool inclDisabled=false) const
size_t size() const
Definition: PmaTrack3D.h:89
std::vector< std::pair< TVector3, size_t > > pma::PMAlgVertexing::getKinks ( const pma::TrkCandidateColl tracks) const

Definition at line 641 of file PMAlgVertexing.cxx.

References pma::Node3D::IsBranching(), pma::Node3D::IsVertex(), n, pma::Track3D::Nodes(), pma::Node3D::Point3D(), and pma::TrkCandidateColl::size().

643 {
644  std::vector<std::pair<TVector3, size_t>> ksel;
645  for (size_t t = 0; t < tracks.size(); ++t) {
646  pma::Track3D const* trk = tracks[t].Track();
647  for (size_t n = 1; n < trk->Nodes().size() - 1; ++n) {
648  pma::Node3D const* node = trk->Nodes()[n];
649  if (!node->IsBranching() && node->IsVertex()) {
650  ksel.emplace_back(std::pair<TVector3, size_t>(node->Point3D(), t));
651  }
652  }
653  }
654  return ksel;
655 }
TVector3 const & Point3D() const
Definition: PmaNode3D.h:44
size_t size() const
bool IsVertex() const
Check fIsVertex flag.
Definition: PmaNode3D.h:65
bool IsBranching() const
Belongs to more than one track?
Definition: PmaNode3D.cxx:418
Char_t n[5]
std::vector< pma::Node3D * > const & Nodes() const noexcept
Definition: PmaTrack3D.h:274
std::vector< std::pair< TVector3, std::vector< std::pair< size_t, bool > > > > pma::PMAlgVertexing::getVertices ( const pma::TrkCandidateColl tracks,
bool  onlyBranching = false 
) const

Definition at line 601 of file PMAlgVertexing.cxx.

References pma::Track3D::front(), pma::Node3D::IsBranching(), n, pma::Track3D::Nodes(), pma::Hit3D::Point3D(), pma::TrkCandidateColl::size(), and lar::dump::vector().

602 {
603  std::vector<std::pair<TVector3, std::vector<std::pair<size_t, bool>>>> vsel;
604  std::vector<pma::Node3D const*> bnodes;
605 
606  for (size_t t = 0; t < tracks.size(); ++t) {
607  pma::Track3D const* trk = tracks[t].Track();
608  pma::Node3D const* firstNode = trk->Nodes().front();
609  if (!(onlyBranching || firstNode->IsBranching())) {
610  std::vector<std::pair<size_t, bool>> tidx;
611  tidx.emplace_back(std::pair<size_t, bool>(t, true));
612  vsel.emplace_back(
613  std::pair<TVector3, std::vector<std::pair<size_t, bool>>>(trk->front()->Point3D(), tidx));
614  }
615 
616  bool pri = true;
617  for (auto node : trk->Nodes())
618  if (node->IsBranching()) {
619  bool found = false;
620  for (size_t n = 0; n < bnodes.size(); n++)
621  if (node == bnodes[n]) {
622  vsel[n].second.emplace_back(std::pair<size_t, bool>(t, pri));
623  found = true;
624  break;
625  }
626  if (!found) {
627  std::vector<std::pair<size_t, bool>> tidx;
628  tidx.emplace_back(std::pair<size_t, bool>(t, pri));
629  vsel.emplace_back(
630  std::pair<TVector3, std::vector<std::pair<size_t, bool>>>(node->Point3D(), tidx));
631  bnodes.push_back(node);
632  }
633  pri = false;
634  }
635  }
636 
637  return vsel;
638 }
size_t size() const
pma::Hit3D const * front() const
Definition: PmaTrack3D.h:87
TVector3 const & Point3D() const
Definition: PmaHit3D.h:50
auto vector(Vector const &v)
Returns a manipulator which will print the specified array.
Definition: DumpUtils.h:289
bool IsBranching() const
Belongs to more than one track?
Definition: PmaNode3D.cxx:418
Char_t n[5]
std::vector< pma::Node3D * > const & Nodes() const noexcept
Definition: PmaTrack3D.h:274
bool pma::PMAlgVertexing::has ( const std::vector< size_t > &  v,
size_t  idx 
) const
inlineprivate

Definition at line 85 of file PMAlgVertexing.h.

Referenced by findKinksOnTracks().

86  {
87  for (auto c : v)
88  if (c == idx) return true;
89  return false;
90  }
bool pma::PMAlgVertexing::isSingleParticle ( pma::Track3D trk1,
pma::Track3D trk2 
) const
private

Check if colinear in 3D and dQ/dx with no significant step.

Definition at line 404 of file PMAlgVertexing.cxx.

References convolute(), getdQdx(), and pma::Track3D::Segments().

Referenced by mergeBrokenTracks().

405 {
406  const double minCos = 0.996194698; // 5 deg (is it ok?)
407  double segCos =
408  trk1->Segments().back()->GetDirection3D().Dot(trk2->Segments().front()->GetDirection3D());
409  if (segCos < minCos) {
410  mf::LogVerbatim("pma::PMAlgVertexing") << " has large angle, cos: " << segCos;
411  return false;
412  }
413 
414  const size_t stepShapeLen = 16;
415  const size_t stepShapeHalf = stepShapeLen >> 1;
416  const double stepShape[stepShapeLen] = {
417  -1., -1., -1., -1., -1., -1., -1., -1., 1., 1., 1., 1., 1., 1., 1., 1.};
418 
419  auto dqdx1 = getdQdx(*trk1);
420  if (dqdx1.size() < stepShapeHalf) return false;
421  auto dqdx2 = getdQdx(*trk2);
422  if (dqdx2.size() < stepShapeHalf) return false;
423 
424  const size_t adcLen =
425  stepShapeLen + 2; // 1 sample before/after to check convolution at 3 points in total
426  const size_t adcHalf = adcLen >> 1;
427 
428  double dqdx[adcLen];
429  for (size_t i = 0; i < adcLen; i++)
430  dqdx[i] = 0.0;
431 
432  bool has_m = true;
433  for (int i = adcHalf - 1, j = dqdx1.size() - 1; i >= 0; i--, j--) {
434  if (j >= 0)
435  dqdx[i] = dqdx1[j].first;
436  else {
437  dqdx[i] = dqdx[i + 1];
438  has_m = false;
439  }
440  }
441  bool has_p = true;
442  for (size_t i = adcHalf, j = 0; i < adcLen; i++, j++) {
443  if (j < dqdx2.size())
444  dqdx[i] = dqdx2[j].first;
445  else {
446  dqdx[i] = dqdx[i - 1];
447  has_p = false;
448  }
449  }
450 
451  double sum_m = 0.0;
452  if (has_m) sum_m = convolute(adcHalf - 1, stepShapeLen, dqdx, stepShape);
453  double sum_0 = convolute(adcHalf, stepShapeLen, dqdx, stepShape);
454  double sum_p = 0.0;
455  if (has_p) sum_p = convolute(adcHalf + 1, stepShapeLen, dqdx, stepShape);
456 
457  const double convMin = 0.8;
458  if ((fabs(sum_m) >= convMin) || (fabs(sum_0) >= convMin) || (fabs(sum_p) >= convMin)) {
459  mf::LogVerbatim("pma::PMAlgVertexing")
460  << " has step in conv.values: " << sum_m << ", " << sum_0 << ", " << sum_p;
461  return false;
462  }
463  else {
464  mf::LogVerbatim("pma::PMAlgVertexing")
465  << " single particle, conv.values: " << sum_m << ", " << sum_0 << ", " << sum_p;
466  return true;
467  }
468 }
MaybeLogger_< ELseverityLevel::ELsev_info, true > LogVerbatim
std::vector< pma::Segment3D * > const & Segments() const noexcept
Definition: PmaTrack3D.h:269
std::vector< std::pair< double, double > > getdQdx(const pma::Track3D &trk) const
Get dQ/dx sequence to detect various features.
double convolute(size_t idx, size_t len, double *adc, double const *shape) const
Get convolution value.
size_t pma::PMAlgVertexing::makeVertices ( detinfo::DetectorPropertiesData const &  detProp,
std::vector< pma::VtxCandidate > &  candidates 
)
private

Definition at line 161 of file PMAlgVertexing.cxx.

References d, pma::Dist2(), fEmTracks, fMinTrackLength, and fOutTracks.

Referenced by run().

163 {
164  bool merged = true;
165  while (merged && (candidates.size() > 1)) {
166  size_t k_best, l_best, k = 0;
167  while (k < candidates.size() - 1) {
168  size_t l = k + 1;
169  while (l < candidates.size()) {
170  if (candidates[l].Has(candidates[k])) {
171  candidates[k] = candidates[l];
172  candidates.erase(candidates.begin() + l);
173  }
174  else if (candidates[k].Has(candidates[l])) {
175  candidates.erase(candidates.begin() + l);
176  }
177  else
178  l++;
179  }
180  k++;
181  }
182 
183  merged = false;
184  double d_thr = 1.0; // 1.0 = max weighted dist. threshold
185  double d, dmin = d_thr;
186 
187  k = 0;
188  while (k < candidates.size() - 1) {
189  size_t l = k + 1;
190  while (l < candidates.size()) {
191  d = candidates[k].Test(candidates[l]);
192  if (d < dmin) {
193  dmin = d;
194  k_best = k;
195  l_best = l;
196  }
197  l++;
198  }
199  k++;
200  }
201  if ((dmin < d_thr) && candidates[k_best].MergeWith(candidates[l_best])) {
202  candidates.erase(candidates.begin() + l_best);
203  merged = true;
204  }
205  }
206 
207  mf::LogVerbatim("pma::PMAlgVertexing") << "*** Vtx candidates: " << candidates.size();
208  std::vector<pma::VtxCandidate> toJoin;
209  bool select = true;
210  while (select) {
211  int s, nmax = 0, c_best = -1;
212  double a, amax = 0.0;
213 
214  for (size_t v = 0; v < candidates.size(); v++) {
215  if (candidates[v].HasLoops()) continue;
216 
217  bool maybeCorrelated = false;
218  for (size_t u = 0; u < toJoin.size(); u++)
219  if (toJoin[u].IsAttached(candidates[v]) || // connected with tracks or close centers
220  (pma::Dist2(toJoin[u].Center(), candidates[v].Center()) < 15.0 * 15.0)) {
221  maybeCorrelated = true;
222  break;
223  }
224  if (maybeCorrelated) continue;
225 
226  s = (int)candidates[v].Size(2 * fMinTrackLength);
227  a = candidates[v].MaxAngle(1.0);
228 
229  if ((s > nmax) || ((s == nmax) && (a > amax))) {
230  nmax = s;
231  amax = a;
232  c_best = v;
233  }
234  /*
235  mf::LogVerbatim("pma::PMAlgVertexing")
236  << "center x:" << candidates[v].Center().X()
237  << " y:" << candidates[v].Center().Y()
238  << " z:" << candidates[v].Center().Z();
239 
240  for (size_t i = 0; i < candidates[v].Size(); i++)
241  mf::LogVerbatim("pma::PMAlgVertexing")
242  << " trk:" << i << " "
243  << candidates[v].Track(i).first->size();
244 
245  mf::LogVerbatim("pma::PMAlgVertexing")
246  << " dist 3D:" << sqrt(candidates[v].Mse())
247  << " 2D:" << sqrt(candidates[v].Mse2D())
248  << " max ang:" << a;
249 */
250  }
251  if (c_best >= 0) {
252  toJoin.push_back(candidates[c_best]);
253  candidates.erase(candidates.begin() + c_best);
254  }
255  else
256  select = false;
257  }
258  mf::LogVerbatim("pma::PMAlgVertexing") << "*** Vtx selected to join: " << toJoin.size();
259 
260  size_t njoined = 0;
261  for (auto& c : toJoin) {
262  if (c.JoinTracks(detProp, fOutTracks, fEmTracks)) njoined++;
263  }
264 
265  return njoined;
266 }
pma::TrkCandidateColl fEmTracks
MaybeLogger_< ELseverityLevel::ELsev_info, true > LogVerbatim
double Dist2(const TVector2 &v1, const TVector2 &v2)
Definition: Utilities.cxx:39
Float_t d
Definition: plot.C:235
pma::TrkCandidateColl fOutTracks
void pma::PMAlgVertexing::mergeBrokenTracks ( pma::TrkCandidateColl trk_input) const
private

Find elastic scattering vertices on tracks, merge back tracks that were split during vertex finding. 3D angle between two tracks and dQ/dx is checked.

Definition at line 470 of file PMAlgVertexing.cxx.

References isSingleParticle(), n, pma::SortedBranchBase::Next(), pma::SortedBranchBase::NextCount(), pma::Track3D::Nodes(), pma::Segment3D::Parent(), pma::SortedObjectBase::Prev(), pma::Track3D::Segments(), and pma::TrkCandidateColl::size().

Referenced by run().

471 {
472  if (trk_input.size() < 2) return;
473 
474  mf::LogVerbatim("pma::PMAlgVertexing") << "Find and merge tracks broken by vertices.";
475  bool merged = true;
476  while (merged) {
477  merged = false;
478  for (size_t t = 0; t < trk_input.size(); t++) {
479  pma::Track3D* trk1 = trk_input[t].Track();
480  pma::Track3D* trk2 = 0;
481 
482  pma::Node3D* node = trk1->Nodes().front();
483  if (node->Prev()) {
484  pma::Segment3D* seg = static_cast<pma::Segment3D*>(node->Prev());
485  trk2 = seg->Parent();
486  if ((trk1 != trk2) && isSingleParticle(trk2, trk1)) // note: reverse order
487  {
488  //merged = true;
489  break;
490  }
491  }
492 
493  trk2 = 0;
494  double c, maxc = 0.0;
495  pma::Vector3D dir1 = trk1->Segments().back()->GetDirection3D();
496  node = trk1->Nodes().back();
497  for (size_t n = 0; n < node->NextCount(); n++) {
498  pma::Segment3D* seg = static_cast<pma::Segment3D*>(node->Next(n));
499  pma::Track3D* tst = seg->Parent();
500  if (tst != trk1) // should always be true: the last node of trk1 is tested
501  {
502  c = dir1.Dot(tst->Segments().front()->GetDirection3D());
503  if (c > maxc) {
504  maxc = c;
505  trk2 = tst;
506  }
507  }
508  }
509  if ((trk2) && isSingleParticle(trk1, trk2)) {
510  //merged = true;
511  break;
512  }
513  }
514  }
515  mf::LogVerbatim("pma::PMAlgVertexing") << "-------- done --------";
516 }
MaybeLogger_< ELseverityLevel::ELsev_info, true > LogVerbatim
size_t size() const
virtual unsigned int NextCount(void) const
Definition: SortedObjects.h:84
recob::tracking::Vector_t Vector3D
Definition: Utilities.h:34
std::vector< pma::Segment3D * > const & Segments() const noexcept
Definition: PmaTrack3D.h:269
virtual pma::SortedObjectBase * Next(unsigned int index=0) const
Definition: SortedObjects.h:77
Char_t n[5]
bool isSingleParticle(pma::Track3D *trk1, pma::Track3D *trk2) const
Check if colinear in 3D and dQ/dx with no significant step.
std::vector< pma::Node3D * > const & Nodes() const noexcept
Definition: PmaTrack3D.h:274
virtual pma::SortedObjectBase * Prev(void) const
Definition: SortedObjects.h:42
pma::Track3D * Parent(void) const
Definition: PmaSegment3D.h:66
void pma::PMAlgVertexing::reset ( )
inline

Definition at line 63 of file PMAlgVertexing.h.

63 { cleanTracks(); }
size_t pma::PMAlgVertexing::run ( const detinfo::DetectorPropertiesData detProp,
pma::TrkCandidateColl trk_input 
)

Copy input tracks, find 3D vertices, connect tracks, break them or flip if needed, reoptimize track structures. Result is returned as a collection of new tracks, that replaces content of trk_input (old tracks are deleted). Vertices can be accessed with getVertices function.

Definition at line 269 of file PMAlgVertexing.cxx.

References collectTracks(), fEmTracks, fFindKinks, findKinksOnTracks(), firstPassCandidates(), fOutTracks, makeVertices(), mergeBrokenTracks(), secondPassCandidates(), pma::TrkCandidateColl::size(), and sortTracks().

Referenced by pma::PMAlgFitter::build(), and pma::PMAlgTracker::build().

271 {
272  if (fFindKinks) findKinksOnTracks(detProp, trk_input);
273 
274  if (trk_input.size() < 2) {
275  mf::LogWarning("pma::PMAlgVertexing") << "need min two source tracks!";
276  return 0;
277  }
278 
279  sortTracks(trk_input); // copy input and split by tag/size
280 
281  size_t nvtx = 0;
282  mf::LogVerbatim("pma::PMAlgVertexing") << "Pass #1:";
283  //std::cout << "Pass #1:" << std::endl;
284  if (fOutTracks.size() > 1) {
285  size_t nfound = 0;
286  do {
287  auto candidates = firstPassCandidates();
288  if (candidates.size()) {
289  nfound = makeVertices(detProp, candidates);
290  nvtx += nfound;
291  }
292  else
293  nfound = 0;
294  } while (nfound > 0);
295  mf::LogVerbatim("pma::PMAlgVertexing") << " " << nvtx << " vertices.";
296  //std::cout << " " << nvtx << " vertices." << std::endl;
297  }
298  else
299  mf::LogVerbatim("pma::PMAlgVertexing") << " ...short tracks only.";
300 
301  mf::LogVerbatim("pma::PMAlgVertexing") << "Pass #2:";
302  //std::cout << "Pass #2:" << std::endl;
303  if (fOutTracks.size() && fEmTracks.size()) {
304  size_t nfound = 1; // just to start
305  while (nfound && fEmTracks.size()) {
306  auto candidates = secondPassCandidates();
307  if (candidates.size()) {
308  nfound = makeVertices(detProp, candidates);
309  nvtx += nfound;
310  }
311  else
312  nfound = 0;
313  }
314  mf::LogVerbatim("pma::PMAlgVertexing") << " " << nvtx << " vertices.";
315  //std::cout << " " << nvtx << " vertices." << std::endl;
316  }
317  else
318  mf::LogVerbatim("pma::PMAlgVertexing") << " ...no tracks.";
319 
320  collectTracks(trk_input);
321 
322  mergeBrokenTracks(trk_input);
323 
324  return nvtx;
325 }
pma::TrkCandidateColl fEmTracks
MaybeLogger_< ELseverityLevel::ELsev_info, true > LogVerbatim
size_t size() const
std::vector< pma::VtxCandidate > firstPassCandidates() const
std::vector< pma::VtxCandidate > secondPassCandidates() const
void collectTracks(pma::TrkCandidateColl &result)
pma::TrkCandidateColl fOutTracks
size_t makeVertices(detinfo::DetectorPropertiesData const &detProp, std::vector< pma::VtxCandidate > &candidates)
MaybeLogger_< ELseverityLevel::ELsev_warning, false > LogWarning
void sortTracks(const pma::TrkCandidateColl &trk_input)
void findKinksOnTracks(const detinfo::DetectorPropertiesData &detProp, pma::TrkCandidateColl &trk_input) const
Remove penalty on the angle if kink detected and reopt track.
void mergeBrokenTracks(pma::TrkCandidateColl &trk_input) const
size_t pma::PMAlgVertexing::run ( pma::TrkCandidateColl trk_input,
const std::vector< TVector3 > &  vtx_input 
)

Copy input tracks, use provided 3D vertices to connect tracks, break tracks or flip if needed, reoptimize track structures. Result is returned as a collection of new tracks, that replaces content of trk_input (old tracks are deleted). Input vertices that were actually associated to tracks are copied to the output collection (use getVertices function).

Definition at line 328 of file PMAlgVertexing.cxx.

References sortTracks().

330 {
331  sortTracks(trk_input); // copy input and split by tag/size
332 
333  // ....
334 
335  //collectTracks(trk_input); // return output in place of (deleted) input
336 
337  return 0;
338 }
void sortTracks(const pma::TrkCandidateColl &trk_input)
std::vector< pma::VtxCandidate > pma::PMAlgVertexing::secondPassCandidates ( ) const
private

Definition at line 142 of file PMAlgVertexing.cxx.

References pma::VtxCandidate::Add(), fEmTracks, fMinTrackLength, fOutTracks, pma::VtxCandidate::Mse(), and pma::TrkCandidateColl::size().

Referenced by run().

143 {
144  std::vector<pma::VtxCandidate> candidates;
145  for (size_t t = 0; t < fOutTracks.size(); t++)
146  if (fOutTracks[t].Track()->Length() > fMinTrackLength) {
147  for (size_t u = 0; u < fEmTracks.size(); u++) {
148  pma::VtxCandidate candidate;
149  if (!candidate.Add(fOutTracks[t])) break; // no segments with length > thr
150 
151  if (fOutTracks[t].Track() == fEmTracks[u].Track()) continue;
152 
153  if (candidate.Add(fEmTracks[u]) && (sqrt(candidate.Mse()) < 1.0)) {
154  candidates.push_back(candidate);
155  }
156  }
157  }
158  return candidates;
159 }
pma::TrkCandidateColl fEmTracks
size_t size() const
double Mse() const
pma::TrkCandidateColl fOutTracks
bool Add(const pma::TrkCandidate &trk)
TrackCollectionProxyElement< TrackCollProxy > Track
Proxy to an element of a proxy collection of recob::Track objects.
Definition: Track.h:992
void pma::PMAlgVertexing::sortTracks ( const pma::TrkCandidateColl trk_input)
private

Definition at line 83 of file PMAlgVertexing.cxx.

References cleanTracks(), fEmTracks, fExcludedTracks, fMinTrackLength, fOutTracks, pma::Track3D::kCosmic, pma::Track3D::kEmLike, pma::TrkCandidateColl::size(), and pma::TrkCandidateColl::tracks().

Referenced by run().

84 {
85  cleanTracks();
86 
87  for (auto const& t : trk_input.tracks()) {
88  pma::Track3D* copy = new pma::Track3D(*(t.Track()));
89  int key = t.Key();
90 
91  if ((t.Track()->GetT0() != 0) || // do not create vertices on cosmic muons, now track with any
92  // non-zero t0 is a muon,
93  (t.Track()->HasTagFlag(pma::Track3D::kCosmic))) // tag for track recognized as a cosmic ray
94  // is starting to be used
95  {
96  fExcludedTracks.tracks().emplace_back(copy, key);
97  continue;
98  }
99 
100  double l = t.Track()->Length();
101 
102  if (t.Track()->GetTag() == pma::Track3D::kEmLike) {
103  if (l > 2 * fMinTrackLength)
104  fOutTracks.tracks().emplace_back(copy, key);
105  else
106  fEmTracks.tracks().emplace_back(copy, key);
107  }
108  else {
109  if (l > fMinTrackLength)
110  fOutTracks.tracks().emplace_back(copy, key);
111  else
112  fEmTracks.tracks().emplace_back(copy, key);
113  }
114  }
115  mf::LogVerbatim("pma::PMAlgVertexing") << "long tracks: " << fOutTracks.size() << std::endl;
116  mf::LogVerbatim("pma::PMAlgVertexing")
117  << "em and short tracks: " << fEmTracks.size() << std::endl;
118  mf::LogVerbatim("pma::PMAlgVertexing")
119  << "excluded cosmic tracks: " << fExcludedTracks.size() << std::endl;
120 }
pma::TrkCandidateColl fEmTracks
MaybeLogger_< ELseverityLevel::ELsev_info, true > LogVerbatim
size_t size() const
pma::TrkCandidateColl fOutTracks
pma::TrkCandidateColl fExcludedTracks
std::vector< TrkCandidate > const & tracks() const
void pma::PMAlgVertexing::splitMergedTracks ( pma::TrkCandidateColl trk_input) const
private

Split track and add vertex and reoptimize when dQ/dx step detected.

Definition at line 519 of file PMAlgVertexing.cxx.

References pma::TrkCandidateColl::size().

520 {
521  if (trk_input.size() < 1) return;
522 
523  mf::LogVerbatim("pma::PMAlgVertexing") << "Find missed vtx by dQ/dx steps along merged tracks.";
524  size_t t = 0;
525  while (t < trk_input.size()) {
526  t++;
527  }
528  mf::LogVerbatim("pma::PMAlgVertexing") << "-------- done --------";
529 }
MaybeLogger_< ELseverityLevel::ELsev_info, true > LogVerbatim
size_t size() const

Member Data Documentation

pma::TrkCandidateColl pma::PMAlgVertexing::fEmTracks
private
pma::TrkCandidateColl pma::PMAlgVertexing::fExcludedTracks
private

Definition at line 118 of file PMAlgVertexing.h.

Referenced by cleanTracks(), collectTracks(), and sortTracks().

bool pma::PMAlgVertexing::fFindKinks
private

Definition at line 129 of file PMAlgVertexing.h.

Referenced by PMAlgVertexing(), and run().

double pma::PMAlgVertexing::fKinkMinDeg
private

Definition at line 131 of file PMAlgVertexing.h.

Referenced by findKinksOnTracks(), and PMAlgVertexing().

double pma::PMAlgVertexing::fKinkMinStd
private

Definition at line 132 of file PMAlgVertexing.h.

Referenced by findKinksOnTracks(), and PMAlgVertexing().

double pma::PMAlgVertexing::fMinTrackLength
private

Definition at line 126 of file PMAlgVertexing.h.

Referenced by makeVertices(), PMAlgVertexing(), secondPassCandidates(), and sortTracks().

pma::TrkCandidateColl pma::PMAlgVertexing::fOutTracks
private
pma::TrkCandidateColl pma::PMAlgVertexing::fShortTracks
private

Definition at line 117 of file PMAlgVertexing.h.

Referenced by cleanTracks(), and collectTracks().


The documentation for this class was generated from the following files: