Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2021-02-14 14:31:41

0001 #ifndef CkfPattern_TempTrajectory_H
0002 #define CkfPattern_TempTrajectory_H
0003 
0004 #include "TrackingTools/PatternTools/interface/TrajectoryMeasurement.h"
0005 #include "DataFormats/TrackCandidate/interface/TrajectoryStopReasons.h"
0006 #include "DataFormats/TrajectorySeed/interface/PropagationDirection.h"
0007 #include "DataFormats/TrackingRecHit/interface/TrackingRecHit.h"
0008 #include "DataFormats/Common/interface/OwnVector.h"
0009 #include "FWCore/Utilities/interface/Visibility.h"
0010 
0011 #include <vector>
0012 #include <algorithm>
0013 #include <limits>
0014 #include "TrackingTools/PatternTools/interface/bqueue.h"
0015 
0016 #include "TrackingTools/PatternTools/interface/Trajectory.h"
0017 
0018 /** A class for detailed particle trajectory representation.
0019  *  It is used during trajectory building to "grow" a trajectory.
0020  *  The trajectory is represented as an ordered sequence of 
0021  *  TrajectoryMeasurement objects with a stack-like interface.
0022  *  The measurements are added to the Trajectory in the order of
0023  *  increasing precision: each new TrajectoryMeasurement is assumed to improve
0024  *  the precision of the last one, normally by adding a constraint from 
0025  *  a new RecHit.
0026  *     However the Trajectory class does not have the means to verify
0027  *  that measurements are added in the correct order, and thus cannot
0028  *  guarantee the order, which is the responsibility of the 
0029  *  TrajectoryBuilder. The Trajectory provides some security by
0030  *  allowing to add or remove measurements only on one of it's ends,
0031  *  with push(TM) and pop() methods. The last measurement in a Trajectory
0032  *  can thus be either the innermost (closest to the interaction point)
0033  *  or the outermost, depending on the way the Trajectory was built.
0034  *  The direction of building is represented as a PropagationDirection,
0035  *  which has two possible values: alongMomentum (outwards) and
0036  *  oppositeToMomentum (inwards), and is accessed with the direction()
0037  *  method.
0038  */
0039 
0040 class TempTrajectory {
0041 public:
0042   typedef cmsutils::bqueue<TrajectoryMeasurement> DataContainer;
0043   typedef TrackingRecHit::ConstRecHitContainer ConstRecHitContainer;
0044   typedef ConstRecHitContainer RecHitContainer;
0045 
0046   /** Default constructor of an empty trajectory with undefined seed and 
0047    * undefined direction. This constructor is necessary in order to transiently
0048    * copy vector<Trajectory> in the edm::Event
0049    */
0050 
0051   TempTrajectory() {}
0052 
0053   /** Constructor of an empty trajectory with defined direction.
0054    *  No check is made in the push method that measurements are
0055    *  added in the correct direction.
0056    */
0057   TempTrajectory(PropagationDirection dir, unsigned char nhseed)
0058       : theDirection(dir), theValid(true), theNHseed(nhseed) {}
0059 
0060   TempTrajectory(TempTrajectory const& rh) = default;
0061   TempTrajectory& operator=(TempTrajectory const& rh) = default;
0062 
0063   TempTrajectory(TempTrajectory&& rh) noexcept
0064       : theData(std::move(rh.theData)),
0065         theChiSquared(rh.theChiSquared),
0066         theNumberOfFoundHits(rh.theNumberOfFoundHits),
0067         theNumberOfFoundPixelHits(rh.theNumberOfFoundPixelHits),
0068         theNumberOfLostHits(rh.theNumberOfLostHits),
0069         theNumberOfTrailingFoundHits(rh.theNumberOfTrailingFoundHits),
0070         theNumberOfCCCBadHits_(rh.theNumberOfCCCBadHits_),
0071         theDirection(rh.theDirection),
0072         theValid(rh.theValid),
0073         theNHseed(rh.theNHseed),
0074         theNLoops(rh.theNLoops),
0075         theDPhiCache(rh.theDPhiCache),
0076         theCCCThreshold_(rh.theCCCThreshold_),
0077         stopReason_(rh.stopReason_) {}
0078 
0079   TempTrajectory& operator=(TempTrajectory&& rh) noexcept {
0080     using std::swap;
0081     swap(theData, rh.theData);
0082     theChiSquared = rh.theChiSquared;
0083     theNumberOfFoundHits = rh.theNumberOfFoundHits;
0084     theNumberOfFoundPixelHits = rh.theNumberOfFoundPixelHits;
0085     theNumberOfLostHits = rh.theNumberOfLostHits;
0086     theNumberOfTrailingFoundHits = rh.theNumberOfTrailingFoundHits;
0087     theNumberOfCCCBadHits_ = rh.theNumberOfCCCBadHits_;
0088     theDirection = rh.theDirection;
0089     theValid = rh.theValid;
0090     theNHseed = rh.theNHseed;
0091     theNLoops = rh.theNLoops;
0092     theDPhiCache = rh.theDPhiCache;
0093     theCCCThreshold_ = rh.theCCCThreshold_;
0094     stopReason_ = rh.stopReason_;
0095     return *this;
0096   }
0097 
0098   /// construct TempTrajectory from standard Trajectory
0099   explicit TempTrajectory(Trajectory&& traj);
0100 
0101   /// destruct a TempTrajectory
0102   ~TempTrajectory() {}
0103 
0104   /** Add a new measurement to a Trajectory.
0105    *  The Chi2 of the trajectory is incremented by the value
0106    *  of tm.estimate() . 
0107    */
0108   void push(const TrajectoryMeasurement& tm) { push(tm, tm.estimate()); }
0109 
0110   void push(TrajectoryMeasurement&& tm) { push(std::forward<TrajectoryMeasurement>(tm), tm.estimate()); }
0111 
0112   template <typename... Args>
0113   void emplace(Args&&... args) {
0114     theData.emplace_back(std::forward<Args>(args)...);
0115     pushAux(theData.back().estimate());
0116   }
0117 
0118   /** Add a new sets of measurements to a Trajectory
0119    *  The sorting of hits in the other trajectory must match the one
0120    *  inside this trajectory (that is, both along or both opposite to momentum)
0121    *  (the input segment will be reset to an empty one)
0122    */
0123   void push(TempTrajectory const& segment);
0124 
0125   /** Add a new sets of measurements to a Trajectory
0126    *  Exactly like push(TempTrajectory), but it doesn't copy the data
0127    *  (the input segment will be reset to an empty one)
0128    */
0129   void join(TempTrajectory& segment);
0130 
0131   /** same as the one-argument push, but the trajectory Chi2 is incremented 
0132    *  by chi2Increment. Useful e.g. in trajectory smoothing.
0133    */
0134   void push(const TrajectoryMeasurement& tm, double chi2Increment) {
0135     theData.push_back(tm);
0136     pushAux(chi2Increment);
0137   }
0138 
0139   void push(TrajectoryMeasurement&& tm, double chi2Increment) {
0140     theData.push_back(std::move(tm));
0141     pushAux(chi2Increment);
0142   }
0143 
0144   template <typename... Args>
0145   void emplace(double chi2Increment, Args&&... args) {  // works only because the first Arg is never a double!
0146     theData.emplace_back(std::forward<Args>(args)...);
0147     pushAux(chi2Increment);
0148   }
0149 
0150   /** Remove the last measurement from the trajectory.
0151    */
0152   void pop();
0153 
0154   /** Access to the last measurement.
0155    *  It's the most precise one in a trajectory before smoothing.
0156    *  It's the outermost measurement if direction() == alongMomentum,
0157    *  the innermost one if direction() == oppositeToMomentum.
0158    */
0159   const TrajectoryMeasurement& lastMeasurement() const {
0160     check();
0161     return theData.back();
0162   }
0163 
0164   /** Access to the first measurement.
0165    *  It is the least precise one in a trajectory before smoothing.
0166    *  It is precise in a smoothed trajectory. 
0167    *  It's the innermost measurement if direction() == alongMomentum,
0168    *  the outermost one if direction() == oppositeToMomentum.
0169    */
0170   const TrajectoryMeasurement& firstMeasurement() const {
0171     check();
0172     return theData.front();
0173   }
0174 
0175   /** Return all measurements in a container.
0176    */
0177   const DataContainer& measurements() const { return theData; }
0178 
0179   /** Number of valid RecHits used to determine the trajectory.
0180    *  Can be less than the number of measurements in data() since
0181    *  detector layers crossed without using RecHits from them are also 
0182    *  stored as measurements.
0183    */
0184   int foundHits() const { return theNumberOfFoundHits; }
0185 
0186   /** Number of valid pixel RecHits used to determine the trajectory.
0187    */
0188   int foundPixelHits() const { return theNumberOfFoundPixelHits; }
0189 
0190   /** Number of detector layers crossed without valid RecHits.
0191    *  Used mainly as a criteria for abandoning a trajectory candidate
0192    *  during trajectory building.
0193    */
0194   int lostHits() const { return theNumberOfLostHits; }
0195 
0196   /** Number of valid RecHits at the end of the trajectory after last lost hit.
0197    */
0198   int trailingFoundHits() const { return theNumberOfTrailingFoundHits; }
0199 
0200   /** Number of hits that are not compatible with the CCC used during
0201    *  patter recognition. Used mainly as a criteria for abandoning a
0202    *  trajectory candidate during trajectory building.
0203    */
0204   int cccBadHits() const { return theNumberOfCCCBadHits_; }
0205 
0206   //number of hits in seed
0207   unsigned int seedNHits() const { return theNHseed; }
0208 
0209   /// True if trajectory has no measurements.
0210   bool empty() const { return theData.empty(); }
0211 
0212   /// Value of the raw Chi2 of the trajectory, not normalised to the N.D.F.
0213   float chiSquared() const { return theChiSquared; }
0214 
0215   /** Direction of "growing" of the trajectory. 
0216    *  Possible values are alongMomentum (outwards) and 
0217    *  oppositeToMomentum (inwards).
0218    */
0219   PropagationDirection direction() const;
0220 
0221   /** Returns true if the Trajectory is valid.
0222    *  Trajectories are invalidated e.g. during ambiguity resolution.
0223    */
0224   bool isValid() const { return theValid; }
0225 
0226   /// Method to invalidate a trajectory. Useful during ambiguity resolution.
0227   void invalidate() { theValid = false; }
0228 
0229   /** Definition of inactive Det from the Trajectory point of view.
0230    */
0231   static bool inactive(  //const Det& det
0232   ) {
0233     return false;
0234   }  //FIXME
0235 
0236   /// Redundant method, returns the layer of lastMeasurement() .
0237   const DetLayer* lastLayer() const {
0238     check();
0239     return theData.back().layer();
0240   }
0241 
0242   /// Convert to a standard Trajectory
0243   Trajectory toTrajectory() const;
0244 
0245   /// Pops out all the invalid hits on the tail
0246   void popInvalidTail();
0247 
0248   /// accessor to the delta phi angle betweem the directions of the two measurements on the last
0249   /// two layers crossed by the trajectory
0250   float dPhiCacheForLoopersReconstruction() const { return theDPhiCache; }
0251 
0252   /// method to set the delta phi angle betweem the directions of the two measurements on the last
0253   /// two layers crossed by the trajectory
0254   void setDPhiCacheForLoopersReconstruction(float dphi) { theDPhiCache = dphi; }
0255 
0256   bool isLooper() const { return (theNLoops > 0); }
0257   signed char nLoops() const { return theNLoops; }
0258 
0259   void setNLoops(signed char value) { theNLoops = value; }
0260   void incrementLoops() { theNLoops++; }
0261 
0262   StopReason stopReason() const { return stopReason_; }
0263   void setStopReason(StopReason s) { stopReason_ = s; }
0264 
0265   int numberOfCCCBadHits(float ccc_threshold);
0266 
0267   static bool lost(const TrackingRecHit& hit) dso_internal;
0268 
0269 private:
0270   /** Definition of what it means for a hit to be "lost".
0271    *  This definition is also used by the TrajectoryBuilder.
0272    */
0273   bool badForCCC(const TrajectoryMeasurement& tm) dso_internal;
0274   void updateBadForCCC(float ccc_threshold) dso_internal;
0275 
0276   void pushAux(double chi2Increment);
0277 
0278 private:
0279   DataContainer theData;
0280 
0281   float theChiSquared = 0;
0282 
0283   signed short theNumberOfFoundHits = 0;
0284   signed short theNumberOfFoundPixelHits = 0;
0285   signed short theNumberOfLostHits = 0;
0286   signed short theNumberOfTrailingFoundHits = 0;
0287   signed short theNumberOfCCCBadHits_ = 0;
0288 
0289   // PropagationDirection
0290   signed char theDirection = anyDirection;
0291   bool theValid = false;
0292 
0293   unsigned char theNHseed = 0;
0294 
0295   signed char theNLoops = 0;
0296   float theDPhiCache = 0;
0297   float theCCCThreshold_ = std::numeric_limits<float>::max();
0298   StopReason stopReason_ = StopReason::UNINITIALIZED;
0299 
0300   void check() const;
0301 };
0302 
0303 #endif