File indexing completed on 2025-08-05 08:17:17
0001 #ifndef TRACKRECO_PHCASEEDING_H
0002 #define TRACKRECO_PHCASEEDING_H
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016 #include "PHTrackSeeding.h" // for PHTrackSeeding
0017
0018 #include <tpc/TpcGlobalPositionWrapper.h>
0019
0020 #include <trackbase/TrkrDefs.h> // for cluskey
0021 #include <trackbase_historic/TrackSeed_v2.h>
0022
0023 #include <phool/PHTimer.h> // for PHTimer
0024
0025 #include <Eigen/Core>
0026 #include <Eigen/Dense>
0027
0028 #pragma GCC diagnostic push
0029 #pragma GCC diagnostic ignored "-Wdeprecated-declarations"
0030 #include <boost/geometry/geometries/box.hpp> // for box
0031 #pragma GCC diagnostic pop
0032
0033 #include <boost/geometry/geometries/point.hpp> // for point
0034 #include <boost/geometry/index/rtree.hpp> // for ca
0035
0036 #include <cmath> // for M_PI
0037 #include <cstdint> // for uint64_t
0038 #include <map> // for map
0039 #include <memory>
0040 #include <set>
0041 #include <string> // for string
0042 #include <unordered_map> // for map
0043 #include <unordered_set>
0044 #include <utility> // for pair
0045 #include <vector> // for vector
0046
0047 #include <TFile.h>
0048 #include <TNtuple.h>
0049
0050 class ActsGeometry;
0051 class PHCompositeNode;
0052 class PHTimer;
0053 class SvtxTrack_v3;
0054 class TpcDistortionCorrectionContainer;
0055 class TrkrCluster;
0056
0057 namespace bg = boost::geometry;
0058 namespace bgi = boost::geometry::index;
0059
0060 class PHCASeeding : public PHTrackSeeding
0061 {
0062 public:
0063 static const int _NLAYERS_TPC = 48;
0064 static const int _FIRST_LAYER_TPC = 7;
0065
0066
0067 using point = bg::model::point<float, 2, bg::cs::cartesian>;
0068 using box = bg::model::box<point>;
0069 using pointKey = std::pair<point, TrkrDefs::cluskey>;
0070 using coordKey = std::pair<std::array<float, 2>, TrkrDefs::cluskey>;
0071
0072 using keyList = std::vector<TrkrDefs::cluskey>;
0073 using keyLists = std::vector<keyList>;
0074 using keyListPerLayer = std::array<keyList, _NLAYERS_TPC>;
0075 using keySet = std::set<TrkrDefs::cluskey>;
0076
0077 using keyLink = std::pair<TrkrDefs::cluskey, TrkrDefs::cluskey>;
0078 using keyLinks = std::vector<keyLink>;
0079 using keyLinkPerLayer = std::array<std::vector<keyLink>, _NLAYERS_TPC>;
0080
0081 using PositionMap = std::unordered_map<TrkrDefs::cluskey, Acts::Vector3>;
0082
0083 std::array<float, 55> dZ_per_layer{};
0084 std::array<float, 55> dphi_per_layer{};
0085
0086 PHCASeeding(
0087 const std::string& name = "PHCASeeding",
0088 unsigned int start_layer = 7,
0089 unsigned int end_layer = 55,
0090 unsigned int min_nhits_per_cluster = 0,
0091 unsigned int min_clusters_per_track = 5,
0092 const unsigned int nlayers_maps = 3,
0093 const unsigned int nlayers_intt = 4,
0094 const unsigned int nlayers_tpc = 48,
0095 float neighbor_phi_width = .02,
0096 float neighbor_z_width = .01,
0097 float maxSinPhi = 0.999
0098
0099 );
0100
0101 ~PHCASeeding() override {}
0102 void SetSplitSeeds(bool opt = true) { _split_seeds = opt; }
0103 void SetLayerRange(unsigned int layer_low, unsigned int layer_up)
0104 {
0105 _start_layer = layer_low;
0106 _end_layer = layer_up;
0107 }
0108 void SetSearchWindow(float z_width, float phi_width)
0109 {
0110 _neighbor_z_width = z_width;
0111 _neighbor_phi_width = phi_width;
0112 }
0113 void SetClusAdd_delta_window(float _dzdr_cutoff, float _dphidr2_cutoff)
0114 {
0115 _clusadd_delta_dzdr_window = _dzdr_cutoff;
0116 _clusadd_delta_dphidr2_window = _dphidr2_cutoff;
0117 }
0118 void SetMinHitsPerCluster(unsigned int minHits) { _min_nhits_per_cluster = minHits; }
0119 void SetMinClustersPerTrack(unsigned int minClus) { _min_clusters_per_track = minClus; }
0120 void SetNClustersPerSeedRange(unsigned int minClus, unsigned int maxClus)
0121 {
0122 _min_clusters_per_seed = minClus;
0123 _max_clusters_per_seed = maxClus;
0124 if (_min_clusters_per_seed < 3)
0125 {
0126 std::cout << " Error in SetNClustersPerSeedRange: " << __FILE__
0127 << " min value cannot be less than three." << std::endl;
0128 assert(false);
0129 }
0130 }
0131
0132
0133 void set_field_dir(const double) {}
0134 void magFieldFile(const std::string&) {}
0135 void useConstBField(bool) {}
0136 void constBField(float) {}
0137
0138 void useFixedClusterError(bool opt) { _use_fixed_clus_err = opt; }
0139 void setFixedClusterError(int i, double val) { _fixed_clus_err.at(i) = val; }
0140 void set_pp_mode(bool mode) { _pp_mode = mode; }
0141 void reject_zsize1_clusters(bool mode){_reject_zsize1 = mode;}
0142 void setNeonFraction(double frac) { Ne_frac = frac; };
0143 void setArgonFraction(double frac) { Ar_frac = frac; };
0144 void setCF4Fraction(double frac) { CF4_frac = frac; };
0145 void setNitrogenFraction(double frac) { N2_frac = frac; };
0146 void setIsobutaneFraction(double frac) { isobutane_frac = frac; };
0147
0148 protected:
0149 int Setup(PHCompositeNode* topNode) override;
0150 int Process(PHCompositeNode* topNode) override;
0151 int InitializeGeometry(PHCompositeNode* topNode);
0152
0153 int End() override;
0154
0155 private:
0156 bool _save_clus_proc = false;
0157 TFile* _f_clustering_process = nullptr;
0158 int _tupout_count = -1;
0159 int _n_tupchains = -1;
0160
0161 TNtuple* _tupclus_all = nullptr;
0162 TNtuple* _tupclus_links = nullptr;
0163 TNtuple* _tupclus_bilinks = nullptr;
0164 TNtuple* _tupclus_seeds = nullptr;
0165 TNtuple* _tupclus_grown_seeds = nullptr;
0166
0167 TNtuple* _tup_chainbody = nullptr;
0168 TNtuple* _tup_chainfork = nullptr;
0169
0170 TNtuple* _tupwin_link = nullptr;
0171 TNtuple* _tupwin_cos_angle = nullptr;
0172 TNtuple* _tupwin_seed23 = nullptr;
0173 TNtuple* _tupwin_seedL1 = nullptr;
0174
0175 TNtuple* _search_windows = nullptr;
0176
0177
0178 void write_tuples();
0179 void fill_tuple(TNtuple*, float, TrkrDefs::cluskey, const Acts::Vector3&) const;
0180 void fill_tuple_with_seed(TNtuple*, const keyList&, const PositionMap&) const;
0181 void process_tupout_count();
0182 void FillTupWinLink(bgi::rtree<pointKey, bgi::quadratic<16>>&, const coordKey&, const PositionMap&) const;
0183 void FillTupWinCosAngle(const TrkrDefs::cluskey, const TrkrDefs::cluskey, const TrkrDefs::cluskey, const PositionMap&, double cos_angle, bool isneg) const;
0184 void FillTupWinGrowSeed(const keyList& seed, const keyLink& link, const PositionMap& globalPositions) const;
0185 void fill_split_chains(const keyList& chain, const keyList& keylinks, const PositionMap& globalPositions, int& nchains) const;
0186
0187
0188
0189
0190 class CompKeyToBilink
0191 {
0192 public:
0193 bool operator()(const keyLink& p, const TrkrDefs::cluskey& val) const
0194 {
0195 return p.first < val;
0196 }
0197 bool operator()(const TrkrDefs::cluskey& val, const keyLink& p) const
0198 {
0199 return val < p.first;
0200 }
0201 };
0202 std::pair<std::vector<keyLink>::iterator, std::vector<keyLink>::iterator> FindBilinks(const TrkrDefs::cluskey& key);
0203
0204
0205 TpcDistortionCorrection m_distortionCorrection;
0206
0207
0208
0209
0210
0211
0212 Acts::Vector3 getGlobalPosition(TrkrDefs::cluskey, TrkrCluster*) const;
0213 std::pair<PositionMap, keyListPerLayer> FillGlobalPositions();
0214 std::pair<keyLinks, keyLinkPerLayer> CreateBiLinks(const PositionMap& globalPositions, const keyListPerLayer& ckeys);
0215 PHCASeeding::keyLists FollowBiLinks(const keyLinks& trackSeedPairs, const keyLinkPerLayer& bilinks, const PositionMap& globalPositions) const;
0216 std::vector<coordKey> FillTree(bgi::rtree<pointKey, bgi::quadratic<16>>&, const keyList&, const PositionMap&, int layer);
0217 int FindSeedsWithMerger(const PositionMap&, const keyListPerLayer&);
0218
0219 void QueryTree(const bgi::rtree<pointKey, bgi::quadratic<16>>& rtree, double phimin, double zmin, double phimax, double zmax, std::vector<pointKey>& returned_values) const;
0220 std::vector<TrackSeed_v2> RemoveBadClusters(const std::vector<keyList>& seeds, const PositionMap& globalPositions) const;
0221 double getMengerCurvature(TrkrDefs::cluskey a, TrkrDefs::cluskey b, TrkrDefs::cluskey c, const PositionMap& globalPositions) const;
0222
0223 void publishSeeds(const std::vector<TrackSeed_v2>& seeds) const;
0224
0225
0226
0227
0228
0229 const unsigned int _nlayers_maps;
0230 const unsigned int _nlayers_intt;
0231 const unsigned int _nlayers_tpc;
0232 unsigned int _start_layer;
0233 unsigned int _end_layer;
0234 unsigned int _min_nhits_per_cluster;
0235 unsigned int _min_clusters_per_track;
0236 unsigned int _max_clusters_per_seed = 6;
0237 unsigned int _min_clusters_per_seed = 6;
0238
0239
0240 float _neighbor_phi_width;
0241 float _neighbor_z_width;
0242 float _clusadd_delta_dzdr_window = 0.5;
0243 float _clusadd_delta_dphidr2_window = 0.005;
0244 float _max_sin_phi;
0245
0246 double _rz_outlier_threshold = 0.1;
0247 double _xy_outlier_threshold = 0.1;
0248 bool _split_seeds = true;
0249 bool _reject_zsize1 = false;
0250 bool _use_fixed_clus_err = false;
0251 bool _pp_mode = false;
0252 std::array<double, 3> _fixed_clus_err = {.1, .1, .1};
0253
0254
0255 ActsGeometry* m_tGeometry{nullptr};
0256
0257
0258 TpcGlobalPositionWrapper m_globalPositionWrapper;
0259
0260 std::unique_ptr<PHTimer> t_seed;
0261 std::unique_ptr<PHTimer> t_fill;
0262 std::unique_ptr<PHTimer> t_makebilinks;
0263 std::unique_ptr<PHTimer> t_makeseeds;
0264
0265 std::array<bgi::rtree<pointKey, bgi::quadratic<16>>, 3> _rtrees;
0266
0267 double Ne_frac = 0.00;
0268 double Ar_frac = 0.75;
0269 double CF4_frac = 0.20;
0270 double N2_frac = 0.00;
0271 double isobutane_frac = 0.05;
0272 };
0273
0274 #endif