CMS 3D CMS Logo

TracksterLinkingbySkeletons.cc
Go to the documentation of this file.
2 #include <Math/VectorUtil.h>
11 #include "TICLGraph.h"
12 
13 namespace {
14  bool isRoundTrackster(std::array<ticl::Vector, 3> const &skeleton) { return (skeleton[0].Z() == skeleton[2].Z()); }
15 
16  bool isGoodTrackster(const ticl::Trackster &trackster,
17  const std::array<ticl::Vector, 3> &skeleton,
18  const unsigned int min_num_lcs,
19  const float min_trackster_energy,
20  const float pca_quality_th) {
21  bool isGood = false;
22 
23  if (isRoundTrackster(skeleton) or trackster.vertices().size() < min_num_lcs or
24  trackster.raw_energy() < min_trackster_energy) {
25  isGood = false;
26  } else {
27  auto const &eigenvalues = trackster.eigenvalues();
28  auto const sum = std::accumulate(std::begin(eigenvalues), std::end(eigenvalues), 0.f);
29  float pcaQuality = eigenvalues[0] / sum;
30  if (pcaQuality > pca_quality_th) {
31  isGood = true;
32  }
33  }
34  return isGood;
35  }
36 
37  //distance between skeletons
38  float projective_distance(const ticl::Vector &point1, const ticl::Vector &point2) {
39  // squared projective distance
40  float r1 = std::sqrt(point1.x() * point1.x() + point1.y() * point1.y());
41  float r2_at_z1 =
42  std::sqrt(point2.x() * point2.x() + point2.y() * point2.y()) * std::abs(point1.z()) / std::abs(point2.z());
43  float delta_phi = reco::deltaPhi(point1.Phi(), point2.Phi());
44  float projective_distance = (r1 - r2_at_z1) * (r1 - r2_at_z1) + r2_at_z1 * r2_at_z1 * delta_phi * delta_phi;
45  LogDebug("TracksterLinkingbySkeletons") << "Computing distance between point : " << point1 << " And point "
46  << point2 << " Distance " << projective_distance << std::endl;
47  return projective_distance;
48  }
49 } // namespace
50 
51 using namespace ticl;
52 
55  cms::Ort::ONNXRuntime const *onnxRuntime)
56  : TracksterLinkingAlgoBase(conf, iC),
57  timing_quality_threshold_(conf.getParameter<double>("track_time_quality_threshold")),
58  del_(conf.getParameter<double>("wind")),
59  min_num_lcs_(conf.getParameter<unsigned int>("min_num_lcs")),
60  min_trackster_energy_(conf.getParameter<double>("min_trackster_energy")),
61  pca_quality_th_(conf.getParameter<double>("pca_quality_th")),
62  dot_prod_th_(conf.getParameter<double>("dot_prod_th")),
63  max_distance_projective_sqr_(conf.getParameter<std::vector<double>>("max_distance_projective_sqr")),
64  min_distance_z_(conf.getParameter<std::vector<double>>("min_distance_z")),
65  max_distance_projective_sqr_closest_points_(
66  conf.getParameter<std::vector<double>>("max_distance_projective_sqr_closest_points")),
67  max_z_distance_closest_points_(conf.getParameter<std::vector<double>>("max_z_distance_closest_points")),
68  cylinder_radius_sqr_(conf.getParameter<std::vector<double>>("cylinder_radius_sqr"))
69 
70 {}
71 
73  // build disks at HGCal front & EM-Had interface for track propagation
74 
75  float zVal = hgcons_->waferZ(1, true);
76  std::pair<float, float> rMinMax = hgcons_->rangeR(zVal, true);
77 
78  float zVal_interface = rhtools_.getPositionLayer(rhtools_.lastLayerEE()).z();
79  std::pair<float, float> rMinMax_interface = hgcons_->rangeR(zVal_interface, true);
80 
81  for (int iSide = 0; iSide < 2; ++iSide) {
82  float zSide = (iSide == 0) ? (-1. * zVal) : zVal;
83  firstDisk_[iSide] =
84  std::make_unique<GeomDet>(Disk::build(Disk::PositionType(0, 0, zSide),
86  SimpleDiskBounds(rMinMax.first, rMinMax.second, zSide - 0.5, zSide + 0.5))
87  .get());
88 
89  zSide = (iSide == 0) ? (-1. * zVal_interface) : zVal_interface;
90  interfaceDisk_[iSide] = std::make_unique<GeomDet>(
91  Disk::build(Disk::PositionType(0, 0, zSide),
93  SimpleDiskBounds(rMinMax_interface.first, rMinMax_interface.second, zSide - 0.5, zSide + 0.5))
94  .get());
95  }
96 }
97 
99  const hgcal::RecHitTools rhtools,
100  const edm::ESHandle<MagneticField> bfieldH,
101  const edm::ESHandle<Propagator> propH) {
102  hgcons_ = hgcons;
103  rhtools_ = rhtools;
104  buildLayers();
105 
106  bfield_ = bfieldH;
107  propagator_ = propH;
108 }
109 
111  const ticl::Trackster &trackster,
112  float lower_percentage,
113  float upper_percentage,
114  const std::vector<reco::CaloCluster> &layerClusters,
115  const hgcal::RecHitTools &rhtools) {
116  auto const &vertices = trackster.vertices();
117  auto const trackster_raw_energy = trackster.raw_energy();
118  // sort vertices by layerId
119  std::vector<unsigned int> sortedVertices(vertices);
120  std::sort(sortedVertices.begin(), sortedVertices.end(), [&layerClusters](unsigned int i, unsigned int j) {
121  return std::abs(layerClusters[i].z()) < std::abs(layerClusters[j].z());
122  });
123 
124  // now loop over sortedVertices and find the layerId that contains the lower_percentage of the energy
125  // and the layerId that contains the upper_percentage of the energy
126  float cumulativeEnergyFraction = 0.f;
127  int innerLayerId = rhtools.getLayerWithOffset(layerClusters[sortedVertices[0]].hitsAndFractions()[0].first);
128  float innerLayerZ = layerClusters[sortedVertices[0]].z();
129  int outerLayerId = rhtools.getLayerWithOffset(layerClusters[sortedVertices.back()].hitsAndFractions()[0].first);
130  float outerLayerZ = layerClusters[sortedVertices.back()].z();
131  bool foundInnerLayer = false;
132  bool foundOuterLayer = false;
133  for (auto const &v : sortedVertices) {
134  auto const &lc = layerClusters[v];
135  auto const &n_lay = rhtools.getLayerWithOffset(lc.hitsAndFractions()[0].first);
136  cumulativeEnergyFraction += lc.energy() / trackster_raw_energy;
137  if (cumulativeEnergyFraction >= lower_percentage and not foundInnerLayer) {
138  innerLayerId = n_lay;
139  innerLayerZ = lc.z();
140  foundInnerLayer = true;
141  }
142  if (cumulativeEnergyFraction >= upper_percentage and not foundOuterLayer) {
143  outerLayerId = n_lay;
144  outerLayerZ = lc.z();
145  foundOuterLayer = true;
146  }
147  }
148  std::array<ticl::Vector, 3> skeleton;
149  int minimumDistanceInLayers = 4;
150  if (outerLayerId - innerLayerId < minimumDistanceInLayers) {
151  skeleton = {{trackster.barycenter(), trackster.barycenter(), trackster.barycenter()}};
152  } else {
153  auto intersectLineWithSurface = [](float surfaceZ, const Vector &origin, const Vector &direction) -> Vector {
154  auto const t = (surfaceZ - origin.Z()) / direction.Z();
155  auto const iX = t * direction.X() + origin.X();
156  auto const iY = t * direction.Y() + origin.Y();
157  auto const iZ = surfaceZ;
158  const Vector intersection(iX, iY, iZ);
159  return intersection;
160  };
161 
162  auto const &t0_p1 = trackster.barycenter();
163  auto const t0_p0 = intersectLineWithSurface(innerLayerZ, t0_p1, trackster.eigenvectors(0));
164  auto const t0_p2 = intersectLineWithSurface(outerLayerZ, t0_p1, trackster.eigenvectors(0));
165  skeleton = {{t0_p0, t0_p1, t0_p2}};
166  std::sort(skeleton.begin(), skeleton.end(), [](Vector &v1, Vector &v2) { return v1.Z() < v2.Z(); });
167  }
168 
169  return skeleton;
170 }
171 
172 bool isInCylinder(const std::array<ticl::Vector, 3> &mySkeleton,
173  const std::array<ticl::Vector, 3> &otherSkeleton,
174  const float radius_sqr) {
175  const auto &first = mySkeleton[0];
176  const auto &last = mySkeleton[2];
177  const auto &pointToCheck = otherSkeleton[0];
178 
179  const auto &cylAxis = last - first;
180  const auto &vecToPoint = pointToCheck - first;
181 
182  auto axisNorm = cylAxis.Dot(cylAxis);
183  auto projLength = vecToPoint.Dot(cylAxis) / axisNorm;
184  bool isWithinLength = projLength >= 0 && projLength <= 1;
185 
186  if (!isWithinLength)
187  return false;
188 
189  const auto &proj = cylAxis * projLength;
190 
191  const auto &pointOnAxis = first + proj;
192 
193  const auto &distance = pointToCheck - pointOnAxis;
194  auto distance2 = distance.Dot(distance);
195 
196  bool isWithinRadius = distance2 <= radius_sqr;
197 
198  return isWithinRadius;
199 }
200 
202  const ticl::Trackster &otherTrackster,
203  const std::array<ticl::Vector, 3> &mySkeleton,
204  const std::array<ticl::Vector, 3> &otherSkeleton) {
205  //do not start links from small/bad tracksters
206  float zVal_interface = rhtools_.getPositionLayer(rhtools_.lastLayerEE()).z();
207  if (!isGoodTrackster(myTrackster, mySkeleton, min_num_lcs_, min_trackster_energy_, pca_quality_th_)) {
208  LogDebug("TracksterLinkingbySkeletons") << "Inner Trackster with energy " << myTrackster.raw_energy() << " Num LCs "
209  << myTrackster.vertices().size() << " NOT GOOD " << std::endl;
210  return false;
211  } else {
212  LogDebug("TracksterLinkingbySkeletons") << "Inner Trackster wi energy " << myTrackster.raw_energy() << " Num LCs "
213  << myTrackster.vertices().size() << " IS GOOD " << std::endl;
214  float proj_distance = projective_distance(mySkeleton[1], otherSkeleton[1]);
215  auto isEE = mySkeleton[1].z() <= zVal_interface ? 0 : 1;
216  bool areAlignedInProjectiveSpace = proj_distance < max_distance_projective_sqr_[isEE];
217  LogDebug("TracksterLinkingbySkeletons")
218  << "\t Trying to compare with outer Trackster with energy " << otherTrackster.raw_energy() << " Num LCS "
219  << otherTrackster.vertices().size() << " Projective distance " << proj_distance << " areAlignedProjective "
220  << areAlignedInProjectiveSpace << " TH " << max_distance_projective_sqr_[isEE] << std::endl;
221  //check if otherTrackster is good
222  if (isGoodTrackster(otherTrackster, otherSkeleton, min_num_lcs_, min_trackster_energy_, pca_quality_th_)) {
223  // if both tracksters are good, then we can check the projective distance between the barycenters.
224  // if the barycenters are aligned, then we check that the two skeletons are aligned
225  if (areAlignedInProjectiveSpace) {
226  auto dotProdSkeletons =
227  ((mySkeleton[2] - mySkeleton[0]).Unit()).Dot((otherSkeleton[2] - otherSkeleton[0]).Unit());
228  bool alignedSkeletons = dotProdSkeletons > dot_prod_th_;
229  LogDebug("TracksterLinkingbySkeletons")
230  << "\t Outer Trackster is Good, checking for skeleton alignment " << alignedSkeletons << " dotProd "
231  << dotProdSkeletons << " Threshold " << dot_prod_th_ << std::endl;
232  if (alignedSkeletons)
233  LogDebug("TracksterLinkingbySkeletons") << "\t\t Linked! " << std::endl;
234  return alignedSkeletons;
235  } else {
236  // we measure the distance between the two closest nodes in the two skeletons
237  LogDebug("TracksterLinkingbySkeletons")
238  << "\t Outer Trackster is not aligned, check skeletons distances " << std::endl;
239  int myClosestPoint = -1;
240  int otherClosestPoint = -1;
241  float minDistance_z = std::numeric_limits<float>::max();
242  for (int i = 0; i < 3; i++) {
243  for (int j = 0; j < 3; j++) {
244  float dist_z = std::abs(mySkeleton[i].Z() - otherSkeleton[j].Z());
245  if (dist_z < minDistance_z) {
246  myClosestPoint = i;
247  otherClosestPoint = j;
248  minDistance_z = dist_z;
249  }
250  }
251  }
252  if (minDistance_z < min_distance_z_[isEE]) {
253  LogDebug("TracksterLinkingbySkeletons")
254  << "\t Trackster have distance in Z " << minDistance_z
255  << "Checking if they are aligned in projective space "
256  << projective_distance(mySkeleton[myClosestPoint], otherSkeleton[otherClosestPoint]) << " TH "
257  << max_distance_projective_sqr_[isEE] << std::endl;
258  if (projective_distance(mySkeleton[myClosestPoint], otherSkeleton[otherClosestPoint]) <
260  LogDebug("TracksterLinkingbySkeletons") << "\t\t Linked! " << std::endl;
261  }
262  return projective_distance(mySkeleton[myClosestPoint], otherSkeleton[otherClosestPoint]) <
264  } else {
265  LogDebug("TracksterLinkingbySkeletons") << "\t\t Not Linked Distance Z " << minDistance_z << std::endl;
266  return false;
267  }
268  }
269  } else {
270  LogDebug("TracksterLinkingbySkeletons")
271  << "\t Outer Trackster is NOT GOOD, check projective space alignment " << areAlignedInProjectiveSpace
272  << " proj_distance " << max_distance_projective_sqr_[isEE] << std::endl;
273  if (areAlignedInProjectiveSpace) {
274  LogDebug("TracksterLinkingbySkeletons") << "\t\t Linked! " << std::endl;
275  return true;
276  } else {
277  LogDebug("TracksterLinkingbySkeletons")
278  << "\t Not aligned in projective space, check distance between closest points in the two skeletons "
279  << std::endl;
280  // we measure the distance between the two closest nodes in the two skeletons
281  int myClosestPoint = -1;
282  int otherClosestPoint = -1;
283  float minDistance_z = std::numeric_limits<float>::max();
284  // we skip the innermost node of mySkeleton
285  for (int i = 1; i < 3; i++) {
286  for (int j = 0; j < 3; j++) {
287  float dist_z = std::abs(mySkeleton[i].Z() - otherSkeleton[j].Z());
288  if (dist_z < minDistance_z) {
289  myClosestPoint = i;
290  otherClosestPoint = j;
291  minDistance_z = dist_z;
292  }
293  }
294  }
295  float d = projective_distance(mySkeleton[myClosestPoint], otherSkeleton[otherClosestPoint]);
296  LogDebug("TracksterLinkingbySkeletons")
297  << "\t\t Distance between closest points " << d << " TH " << 10.f << " Z Distance " << minDistance_z
298  << " TH " << max_distance_projective_sqr_closest_points_[isEE] << std::endl;
300  minDistance_z < max_z_distance_closest_points_[isEE]) {
301  LogDebug("TracksterLinkingbySkeletons") << "\t\t\t Linked! " << d << std::endl;
302  return true;
303  } else {
304  LogDebug("TracksterLinkingbySkeletons") << "Distance between closest point " << d << " Distance in z "
305  << max_z_distance_closest_points_[isEE] << std::endl;
306  bool isInCyl = isInCylinder(mySkeleton, otherSkeleton, cylinder_radius_sqr_[isEE]);
307  LogDebug("TracksterLinkingbySkeletons") << "Two Points are in Cylinder " << isInCylinder << std::endl;
308  if (isInCyl) {
309  LogDebug("TracksterLinkingbySkeletons") << "\t\t\t Linked! " << d << std::endl;
310  }
311  return isInCyl;
312  }
313  }
314  }
315  }
316 }
317 
319  const Inputs &input,
320  std::vector<Trackster> &resultTracksters,
321  std::vector<std::vector<unsigned int>> &linkedResultTracksters,
322  std::vector<std::vector<unsigned int>> &linkedTracksterIdToInputTracksterId) {
323  const auto &tracksters = input.tracksters;
324  const auto &layerClusters = input.layerClusters;
325 
326  // sort tracksters by energy
327  std::vector<unsigned int> sortedTracksters(tracksters.size());
328  std::iota(sortedTracksters.begin(), sortedTracksters.end(), 0);
329  std::sort(sortedTracksters.begin(), sortedTracksters.end(), [&tracksters](unsigned int i, unsigned int j) {
330  return tracksters[i].raw_energy() > tracksters[j].raw_energy();
331  });
332  // fill tiles for trackster linking
333  // tile 0 for negative eta
334  // tile 1 for positive eta
335  std::array<TICLLayerTile, 2> tracksterTile;
336  // loop over tracksters sorted by energy and calculate skeletons
337  // fill tiles for trackster linking
338  std::vector<std::array<ticl::Vector, 3>> skeletons(tracksters.size());
339  for (auto const t_idx : sortedTracksters) {
340  const auto &trackster = tracksters[t_idx];
341  skeletons[t_idx] = findSkeletonNodes(tracksters[t_idx], 0.1, 0.9, layerClusters, rhtools_);
342  tracksterTile[trackster.barycenter().eta() > 0.f].fill(
343  trackster.barycenter().eta(), trackster.barycenter().phi(), t_idx);
344  }
345  std::vector<int> maskReceivedLink(tracksters.size(), 1);
346  std::vector<int> isRootTracksters(tracksters.size(), 1);
347 
348  std::vector<Node> allNodes;
349  for (size_t it = 0; it < tracksters.size(); ++it) {
350  allNodes.emplace_back(it);
351  }
352 
353  // loop over tracksters sorted by energy and link them
354  for (auto const &t_idx : sortedTracksters) {
355  auto const &trackster = tracksters[t_idx];
356  auto const &skeleton = skeletons[t_idx];
357 
358  auto const bary = trackster.barycenter();
359  float eta_min = std::max(abs(bary.eta()) - del_, TileConstants::minEta);
360  float eta_max = std::min(abs(bary.eta()) + del_, TileConstants::maxEta);
361  int tileIndex = bary.eta() > 0.f;
362  const auto &tiles = tracksterTile[tileIndex];
363  std::array<int, 4> search_box = tiles.searchBoxEtaPhi(eta_min, eta_max, bary.phi() - del_, bary.phi() + del_);
364  if (search_box[2] > search_box[3]) {
365  search_box[3] += TileConstants::nPhiBins;
366  }
367 
368  for (int eta_i = search_box[0]; eta_i <= search_box[1]; ++eta_i) {
369  for (int phi_i = search_box[2]; phi_i <= search_box[3]; ++phi_i) {
370  auto &neighbours = tiles[tiles.globalBin(eta_i, (phi_i % TileConstants::nPhiBins))];
371  for (auto n : neighbours) {
372  if (t_idx == n)
373  continue;
374  if (maskReceivedLink[n] == 0 or allNodes[t_idx].isInnerNeighbour(n))
375  continue;
376  if (isGoodTrackster(trackster, skeleton, min_num_lcs_, min_trackster_energy_, pca_quality_th_)) {
377  LogDebug("TracksterLinkingbySkeletons")
378  << "Trying to Link Trackster " << t_idx << " With Trackster " << n << std::endl;
379  if (areCompatible(trackster, tracksters[n], skeleton, skeletons[n])) {
380  LogDebug("TracksterLinkingbySkeletons")
381  << "\t==== LINK: Trackster " << t_idx << " Linked with Trackster " << n << std::endl;
382  maskReceivedLink[n] = 0;
383  allNodes[t_idx].addOuterNeighbour(n);
384  allNodes[n].addInnerNeighbour(t_idx);
385  isRootTracksters[n] = 0;
386  }
387  }
388  }
389  }
390  }
391  }
392 
393  LogDebug("TracksterLinkingbySkeletons") << "**************** FINAL GRAPH **********************" << std::endl;
394  for (auto const &node : allNodes) {
395  if (isRootTracksters[node.getId()]) {
396  LogDebug("TracksterLinkingbySkeletons")
397  << "ISROOT "
398  << " Node " << node.getId() << " position " << tracksters[node.getId()].barycenter() << " energy "
399  << tracksters[node.getId()].raw_energy() << std::endl;
400  } else {
401  LogDebug("TracksterLinkingbySkeletons")
402  << "Node " << node.getId() << " position " << tracksters[node.getId()].barycenter() << " energy "
403  << tracksters[node.getId()].raw_energy() << std::endl;
404  }
405  }
406  LogDebug("TracksterLinkingbySkeletons") << "********************************************************" << std::endl;
407 
408  TICLGraph graph(allNodes, isRootTracksters);
409 
410  int ic = 0;
411  auto const &components = graph.findSubComponents();
412  linkedTracksterIdToInputTracksterId.resize(components.size());
413  for (auto const &comp : components) {
414  LogDebug("TracksterLinkingbySkeletons") << "Component " << ic << " Node: ";
415  std::vector<unsigned int> linkedTracksters;
416  Trackster outTrackster;
417  if (comp.size() == 1) {
418  if (input.tracksters[comp[0]].vertices().size() <= 3) {
419  continue;
420  }
421  }
422  for (auto const &node : comp) {
423  LogDebug("TracksterLinkingbySkeletons") << node << " ";
424  linkedTracksterIdToInputTracksterId[ic].push_back(node);
425  outTrackster.mergeTracksters(input.tracksters[node]);
426  }
427  linkedTracksters.push_back(resultTracksters.size());
428  resultTracksters.push_back(outTrackster);
429  linkedResultTracksters.push_back(linkedTracksters);
430  LogDebug("TracksterLinkingbySkeletons") << "\n";
431  ++ic;
432  }
433 } // linkTracksters
double waferZ(int layer, bool reco) const
constexpr double deltaPhi(double phi1, double phi2)
Definition: deltaPhi.h:26
static DiskPointer build(Args &&... args)
Definition: BoundDisk.h:38
edm::ESHandle< MagneticField > bfield_
static constexpr int nPhiBins
Definition: Common.h:15
const Vector & barycenter() const
Definition: Trackster.h:159
static constexpr float maxEta
Definition: Common.h:13
void linkTracksters(const Inputs &input, std::vector< Trackster > &resultTracksters, std::vector< std::vector< unsigned int >> &linkedResultTracksters, std::vector< std::vector< unsigned int >> &linkedTracksterIdToInputTracksterId) override
bool areCompatible(const ticl::Trackster &myTrackster, const ticl::Trackster &otherTrackster, const std::array< ticl::Vector, 3 > &mySkeleton, const std::array< ticl::Vector, 3 > &otherSkeleton)
static std::string const input
Definition: EdmProvDump.cc:50
int32_t tileIndex(int32_t layer, int32_t ring, int32_t phi)
const std::array< Vector, 3 > & eigenvectors() const
Definition: Trackster.h:161
void mergeTracksters(const Trackster &other)
Definition: Trackster.h:81
TracksterLinkingbySkeletons(const edm::ParameterSet &conf, edm::ConsumesCollector iC, cms::Ort::ONNXRuntime const *onnxRuntime=nullptr)
std::array< ticl::Vector, 3 > findSkeletonNodes(const ticl::Trackster &trackster, float lower_percentage, float upper_percentage, const std::vector< reco::CaloCluster > &layerClusters, const hgcal::RecHitTools &rhtools)
const float raw_energy() const
Definition: Trackster.h:154
T sqrt(T t)
Definition: SSEVec.h:23
The Signals That Services Can Subscribe To This is based on ActivityRegistry and is current per Services can connect to the signals distributed by the ActivityRegistry in order to monitor the activity of the application Each possible callback has some defined which we here list in angle e< void, edm::EventID const &, edm::Timestamp const & > We also list in braces which AR_WATCH_USING_METHOD_ is used for those or
Definition: Activities.doc:12
Abs< T >::type abs(const T &t)
Definition: Abs.h:22
double f[11][100]
std::unique_ptr< GeomDet > interfaceDisk_[2]
static constexpr float minEta
Definition: Common.h:12
d
Definition: ztail.py:151
std::vector< double > max_distance_projective_sqr_closest_points_
std::pair< double, double > rangeR(double z, bool reco) const
std::vector< unsigned int > & vertices()
Definition: Trackster.h:57
std::vector< std::vector< unsigned int > > findSubComponents()
Definition: TICLGraph.cc:20
std::unique_ptr< GeomDet > firstDisk_[2]
GlobalPoint getPositionLayer(int layer, bool nose=false) const
Definition: RecHitTools.cc:152
math::XYZVectorF Vector
Definition: Common.h:42
void initialize(const HGCalDDDConstants *hgcons, const hgcal::RecHitTools rhtools, const edm::ESHandle< MagneticField > bfieldH, const edm::ESHandle< Propagator > propH) override
Definition: Common.h:10
const std::array< float, 3 > & eigenvalues() const
Definition: Trackster.h:160
unsigned int lastLayerEE(bool nose=false) const
Definition: RecHitTools.h:76
bool isInCylinder(const std::array< ticl::Vector, 3 > &mySkeleton, const std::array< ticl::Vector, 3 > &otherSkeleton, const float radius_sqr)
#define LogDebug(id)
unsigned int getLayerWithOffset(const DetId &) const
Definition: RecHitTools.cc:381