File indexing completed on 2024-04-06 12:28:17
0001 #ifndef RecoTracker_MkFitCore_interface_TrackStructures_h
0002 #define RecoTracker_MkFitCore_interface_TrackStructures_h
0003
0004 #include "RecoTracker/MkFitCore/interface/Config.h"
0005 #include "RecoTracker/MkFitCore/interface/Hit.h"
0006 #include "RecoTracker/MkFitCore/interface/Track.h"
0007 #include "RecoTracker/MkFitCore/interface/TrackerInfo.h"
0008
0009 #include <algorithm>
0010 #include <array>
0011
0012 namespace mkfit {
0013
0014 class IterationParams;
0015
0016
0017
0018
0019
0020 struct HoTNode {
0021 HitOnTrack m_hot;
0022 float m_chi2;
0023 int m_prev_idx;
0024 };
0025
0026 struct HitMatch {
0027 int m_hit_idx = -1;
0028 int m_module_id = -1;
0029 float m_chi2 = 1e9;
0030
0031 void reset() {
0032 m_hit_idx = -1;
0033 m_module_id = -1;
0034 m_chi2 = 1e9;
0035 }
0036 };
0037
0038 struct HitMatchPair {
0039 HitMatch M[2];
0040
0041 void reset() {
0042 M[0].reset();
0043 M[1].reset();
0044 }
0045
0046 void consider_hit_for_overlap(int hit_idx, int module_id, float chi2) {
0047 if (module_id == M[0].m_module_id) {
0048 if (chi2 < M[0].m_chi2) {
0049 M[0].m_chi2 = chi2;
0050 M[0].m_hit_idx = hit_idx;
0051 }
0052 } else if (module_id == M[1].m_module_id) {
0053 if (chi2 < M[1].m_chi2) {
0054 M[1].m_chi2 = chi2;
0055 M[1].m_hit_idx = hit_idx;
0056 }
0057 } else {
0058 if (M[0].m_chi2 > M[1].m_chi2) {
0059 if (chi2 < M[0].m_chi2) {
0060 M[0] = {hit_idx, module_id, chi2};
0061 }
0062 } else {
0063 if (chi2 < M[1].m_chi2) {
0064 M[1] = {hit_idx, module_id, chi2};
0065 }
0066 }
0067 }
0068 }
0069
0070 HitMatch* find_overlap(int hit_idx, int module_id) {
0071 if (module_id == M[0].m_module_id) {
0072 if (M[1].m_hit_idx >= 0)
0073 return &M[1];
0074 } else if (module_id == M[1].m_module_id) {
0075 if (M[0].m_hit_idx >= 0)
0076 return &M[0];
0077 } else {
0078 if (M[0].m_chi2 <= M[1].m_chi2) {
0079 if (M[0].m_hit_idx >= 0)
0080 return &M[0];
0081 } else {
0082 if (M[1].m_hit_idx >= 0)
0083 return &M[1];
0084 }
0085 }
0086
0087 return nullptr;
0088 }
0089 };
0090
0091
0092
0093 template <class T>
0094 class CcPool {
0095 public:
0096 void reset(std::size_t size) {
0097 if (size > m_mem.size())
0098 m_mem.resize(size);
0099 m_pos = 0;
0100 m_size = size;
0101 }
0102
0103 void release() {
0104 std::vector<T> tmp;
0105 m_mem.swap(tmp);
0106 m_pos = 0;
0107 m_size = 0;
0108 }
0109
0110 CcPool(std::size_t size = 0) {
0111 if (size)
0112 reset(size);
0113 }
0114
0115 T* allocate(std::size_t n) {
0116 if (m_pos + n > m_size)
0117 throw std::bad_alloc();
0118 T* ret = &m_mem[m_pos];
0119 m_pos += n;
0120 return ret;
0121 }
0122
0123 void deallocate(T* p, std::size_t n) noexcept {
0124
0125 }
0126
0127 private:
0128 std::vector<T> m_mem;
0129 std::size_t m_pos = 0;
0130 std::size_t m_size = 0;
0131 };
0132
0133 template <class T>
0134 class CcAlloc {
0135 public:
0136 typedef T value_type;
0137
0138 CcAlloc(CcPool<T>* p) : m_pool(p) {}
0139
0140 const void* pool_id() const { return m_pool; }
0141
0142 T* allocate(std::size_t n) { return m_pool->allocate(n); }
0143
0144 void deallocate(T* p, std::size_t n) noexcept { m_pool->deallocate(p, n); }
0145
0146 private:
0147 CcPool<T>* m_pool;
0148 };
0149
0150 template <class T, class U>
0151 bool operator==(const CcAlloc<T>& a, const CcAlloc<U>& b) {
0152 return a.pool_id() == b.pool_id();
0153 }
0154
0155
0156
0157 class CombCandidate;
0158
0159 class TrackCand : public TrackBase {
0160 public:
0161 TrackCand() = default;
0162
0163 explicit TrackCand(const TrackBase& base, CombCandidate* ccand) : TrackBase(base), m_comb_candidate(ccand) {
0164
0165 lastHitIdx_ = -1;
0166 nFoundHits_ = 0;
0167 }
0168
0169
0170
0171
0172
0173
0174
0175 CombCandidate* combCandidate() const { return m_comb_candidate; }
0176 void setCombCandidate(CombCandidate* cc) { m_comb_candidate = cc; }
0177
0178 int lastCcIndex() const { return lastHitIdx_; }
0179 int nFoundHits() const { return nFoundHits_; }
0180 int nMissingHits() const { return nMissingHits_; }
0181 int nOverlapHits() const { return nOverlapHits_; }
0182 int nTotalHits() const { return nFoundHits_ + nMissingHits_; }
0183
0184 void setLastCcIndex(int i) { lastHitIdx_ = i; }
0185 void setNFoundHits(int n) { nFoundHits_ = n; }
0186 void setNMissingHits(int n) { nMissingHits_ = n; }
0187 void setNOverlapHits(int n) { nOverlapHits_ = n; }
0188
0189 int nInsideMinusOneHits() const { return nInsideMinusOneHits_; }
0190 int nTailMinusOneHits() const { return nTailMinusOneHits_; }
0191
0192 void setNInsideMinusOneHits(int n) { nInsideMinusOneHits_ = n; }
0193 void setNTailMinusOneHits(int n) { nTailMinusOneHits_ = n; }
0194
0195 int originIndex() const { return m_origin_index; }
0196 void setOriginIndex(int oi) { m_origin_index = oi; }
0197
0198 void resetOverlaps() { m_overlap_hits.reset(); }
0199 void considerHitForOverlap(int hit_idx, int module_id, float chi2) {
0200 m_overlap_hits.consider_hit_for_overlap(hit_idx, module_id, chi2);
0201 }
0202 HitMatch* findOverlap(int hit_idx, int module_id) { return m_overlap_hits.find_overlap(hit_idx, module_id); }
0203
0204
0205
0206 HitOnTrack getLastHitOnTrack() const;
0207 int getLastHitIdx() const;
0208 int getLastHitLyr() const;
0209
0210
0211 int getLastFoundPixelHitLyr() const;
0212 int getLastFoundHitLyr() const;
0213 int nUniqueLayers() const;
0214
0215 int nLayersByTypeEncoded(const TrackerInfo& trk_inf) const;
0216 int nHitsByTypeEncoded(const TrackerInfo& trk_inf) const;
0217
0218 int nPixelDecoded(const int& encoded) const { return encoded % 100; }
0219 int nStereoDecoded(const int& encoded) const { return (encoded / 100) % 100; }
0220 int nMonoDecoded(const int& encoded) const { return (encoded / 10000) % 100; }
0221 int nMatchedDecoded(const int& encoded) const { return encoded / 1000000; }
0222 int nTotMatchDecoded(const int& encoded) const {
0223 return encoded % 100 + (encoded / 100) % 100 + (encoded / 10000) % 100 - encoded / 1000000;
0224 }
0225
0226 void addHitIdx(int hitIdx, int hitLyr, float chi2);
0227 bool popOverlap();
0228
0229 HoTNode& refLastHoTNode();
0230 const HoTNode& refLastHoTNode() const;
0231
0232 void incOverlapCount() { ++nOverlapHits_; }
0233
0234 Track exportTrack(bool remove_missing_hits = false) const;
0235
0236 void resetShortTrack() {
0237 score_ = getScoreWorstPossible();
0238 m_comb_candidate = nullptr;
0239 }
0240
0241 private:
0242 CombCandidate* m_comb_candidate = nullptr;
0243 HitMatchPair m_overlap_hits;
0244
0245
0246 short int nMissingHits_ = 0;
0247 short int nOverlapHits_ = 0;
0248
0249 short int nInsideMinusOneHits_ = 0;
0250 short int nTailMinusOneHits_ = 0;
0251
0252 short int m_origin_index = -1;
0253 };
0254
0255 inline bool sortByScoreTrackCand(const TrackCand& cand1, const TrackCand& cand2) {
0256 return cand1.score() > cand2.score();
0257 }
0258
0259 inline float getScoreCand(const track_score_func& score_func,
0260 const TrackCand& cand1,
0261 bool penalizeTailMissHits = false,
0262 bool inFindCandidates = false) {
0263 int nfoundhits = cand1.nFoundHits();
0264 int noverlaphits = cand1.nOverlapHits();
0265 int nmisshits = cand1.nInsideMinusOneHits();
0266 int ntailmisshits = penalizeTailMissHits ? cand1.nTailMinusOneHits() : 0;
0267 float pt = cand1.pT();
0268 float chi2 = cand1.chi2();
0269
0270 if (chi2 < 0)
0271 chi2 = 0.f;
0272 return score_func(nfoundhits, ntailmisshits, noverlaphits, nmisshits, chi2, pt, inFindCandidates);
0273 }
0274
0275
0276
0277 class CombCandidate {
0278 public:
0279 using trk_cand_vec_type = std::vector<TrackCand, CcAlloc<TrackCand>>;
0280 using allocator_type = CcAlloc<TrackCand>;
0281
0282 enum SeedState_e { Dormant = 0, Finding, Finished };
0283
0284 CombCandidate(const allocator_type& alloc) : m_trk_cands(alloc), m_state(Dormant), m_pickup_layer(-1) {}
0285
0286
0287 CombCandidate(const CombCandidate& o)
0288 : m_trk_cands(o.m_trk_cands),
0289 m_state(o.m_state),
0290 m_pickup_layer(o.m_pickup_layer),
0291 m_lastHitIdx_before_bkwsearch(o.m_lastHitIdx_before_bkwsearch),
0292 m_nInsideMinusOneHits_before_bkwsearch(o.m_nInsideMinusOneHits_before_bkwsearch),
0293 m_nTailMinusOneHits_before_bkwsearch(o.m_nTailMinusOneHits_before_bkwsearch),
0294 m_seed_origin_index(o.m_seed_origin_index),
0295 m_hots_size(o.m_hots_size),
0296 m_hots(o.m_hots) {}
0297
0298
0299 CombCandidate(CombCandidate&& o)
0300 : m_trk_cands(std::move(o.m_trk_cands)),
0301 m_best_short_cand(std::move(o.m_best_short_cand)),
0302 m_state(o.m_state),
0303 m_pickup_layer(o.m_pickup_layer),
0304 m_lastHitIdx_before_bkwsearch(o.m_lastHitIdx_before_bkwsearch),
0305 m_nInsideMinusOneHits_before_bkwsearch(o.m_nInsideMinusOneHits_before_bkwsearch),
0306 m_nTailMinusOneHits_before_bkwsearch(o.m_nTailMinusOneHits_before_bkwsearch),
0307 m_seed_origin_index(o.m_seed_origin_index),
0308 m_hots_size(o.m_hots_size),
0309 m_hots(std::move(o.m_hots)) {
0310
0311
0312
0313
0314
0315 }
0316
0317
0318
0319
0320
0321 CombCandidate& operator=(CombCandidate&& o) {
0322 m_trk_cands = (std::move(o.m_trk_cands));
0323 m_best_short_cand = std::move(o.m_best_short_cand);
0324 m_state = o.m_state;
0325 m_pickup_layer = o.m_pickup_layer;
0326 m_lastHitIdx_before_bkwsearch = o.m_lastHitIdx_before_bkwsearch;
0327 m_nInsideMinusOneHits_before_bkwsearch = o.m_nInsideMinusOneHits_before_bkwsearch;
0328 m_nTailMinusOneHits_before_bkwsearch = o.m_nTailMinusOneHits_before_bkwsearch;
0329 m_seed_origin_index = o.m_seed_origin_index;
0330 m_hots_size = o.m_hots_size;
0331 m_hots = std::move(o.m_hots);
0332
0333 for (auto& tc : m_trk_cands)
0334 tc.setCombCandidate(this);
0335
0336 return *this;
0337 }
0338
0339
0340 bool empty() const { return m_trk_cands.empty(); }
0341 trk_cand_vec_type::size_type size() const { return m_trk_cands.size(); }
0342 void resize(trk_cand_vec_type::size_type count) { m_trk_cands.resize(count); }
0343 TrackCand& operator[](int i) { return m_trk_cands[i]; }
0344 const TrackCand& operator[](int i) const { return m_trk_cands[i]; }
0345 TrackCand& front() { return m_trk_cands.front(); }
0346 const TrackCand& front() const { return m_trk_cands.front(); }
0347 trk_cand_vec_type::reference emplace_back(TrackCand& tc) { return m_trk_cands.emplace_back(tc); }
0348 void clear() { m_trk_cands.clear(); }
0349
0350 void reset(int max_cands_per_seed, int expected_num_hots) {
0351 std::vector<TrackCand, CcAlloc<TrackCand>> tmp(m_trk_cands.get_allocator());
0352 m_trk_cands.swap(tmp);
0353 m_trk_cands.reserve(max_cands_per_seed);
0354
0355 m_best_short_cand.setScore(getScoreWorstPossible());
0356
0357
0358
0359
0360
0361
0362
0363 m_hots.reserve(expected_num_hots);
0364 m_hots_size = 0;
0365 m_hots.clear();
0366
0367 m_lastHitIdx_before_bkwsearch = -1;
0368 m_nInsideMinusOneHits_before_bkwsearch = -1;
0369 m_nTailMinusOneHits_before_bkwsearch = -1;
0370 }
0371
0372 void importSeed(const Track& seed, int seed_idx, const track_score_func& score_func, int region);
0373
0374 int addHit(const HitOnTrack& hot, float chi2, int prev_idx) {
0375 m_hots.push_back({hot, chi2, prev_idx});
0376 return m_hots_size++;
0377 }
0378
0379 void mergeCandsAndBestShortOne(const IterationParams& params,
0380 const track_score_func& score_func,
0381 bool update_score,
0382 bool sort_cands);
0383
0384 void compactifyHitStorageForBestCand(bool remove_seed_hits, int backward_fit_min_hits);
0385 void beginBkwSearch();
0386 void repackCandPostBkwSearch(int i);
0387
0388
0389
0390
0391 int hotsSize() const { return m_hots_size; }
0392 const HoTNode& hot_node(int i) const { return m_hots[i]; }
0393 HoTNode& hot_node_nc(int i) { return m_hots[i]; }
0394 HitOnTrack hot(int i) const { return m_hots[i].m_hot; }
0395
0396 const HoTNode* hotsData() const { return m_hots.data(); }
0397
0398 const TrackCand& refBestShortCand() const { return m_best_short_cand; }
0399 void setBestShortCand(const TrackCand& tc) { m_best_short_cand = tc; }
0400
0401 SeedState_e state() const { return m_state; }
0402 void setState(SeedState_e ss) { m_state = ss; }
0403
0404 int pickupLayer() const { return m_pickup_layer; }
0405
0406 int seed_origin_index() const { return m_seed_origin_index; }
0407
0408 private:
0409 trk_cand_vec_type m_trk_cands;
0410 TrackCand m_best_short_cand;
0411 SeedState_e m_state : 8;
0412 int m_pickup_layer : 16;
0413 short int m_lastHitIdx_before_bkwsearch = -1;
0414 short int m_nInsideMinusOneHits_before_bkwsearch = -1;
0415 short int m_nTailMinusOneHits_before_bkwsearch = -1;
0416 int m_seed_origin_index = -1;
0417 int m_hots_size = 0;
0418 std::vector<HoTNode> m_hots;
0419 };
0420
0421
0422
0423 inline HitOnTrack TrackCand::getLastHitOnTrack() const { return m_comb_candidate->hot(lastHitIdx_); }
0424
0425 inline int TrackCand::getLastHitIdx() const { return m_comb_candidate->hot(lastHitIdx_).index; }
0426
0427 inline int TrackCand::getLastHitLyr() const { return m_comb_candidate->hot(lastHitIdx_).layer; }
0428
0429 inline int TrackCand::getLastFoundHitLyr() const {
0430 int nh = nTotalHits();
0431 int ch = lastHitIdx_;
0432 int ll = -1;
0433 while (--nh >= 0) {
0434 const HoTNode& hot_node = m_comb_candidate->hot_node(ch);
0435 if (hot_node.m_hot.index < 0) {
0436 ch = hot_node.m_prev_idx;
0437 } else {
0438 ll = hot_node.m_hot.layer;
0439 break;
0440 }
0441 }
0442 return ll;
0443 }
0444
0445 inline int TrackCand::getLastFoundPixelHitLyr() const {
0446 int nh = nTotalHits();
0447 int ch = lastHitIdx_;
0448 int ll = -1;
0449 while (--nh >= 0) {
0450 const HoTNode& hot_node = m_comb_candidate->hot_node(ch);
0451 int tl = hot_node.m_hot.layer;
0452 if (hot_node.m_hot.index < 0 || !((0 <= tl && tl <= 3) || (18 <= tl && tl <= 20) || (45 <= tl && tl <= 47))) {
0453 ch = hot_node.m_prev_idx;
0454 } else if ((0 <= tl && tl <= 3) || (18 <= tl && tl <= 20) || (45 <= tl && tl <= 47)) {
0455 ll = hot_node.m_hot.layer;
0456 break;
0457 }
0458 }
0459 return ll;
0460 }
0461
0462 inline int TrackCand::nUniqueLayers() const {
0463 int nUL = 0;
0464 int prevL = -1;
0465 int nh = nTotalHits();
0466 int ch = lastHitIdx_;
0467
0468 while (--nh >= 0) {
0469 const HoTNode& hot_node = m_comb_candidate->hot_node(ch);
0470 int thisL = hot_node.m_hot.layer;
0471 if (thisL >= 0 && (hot_node.m_hot.index >= 0 || hot_node.m_hot.index == Hit::kHitCCCFilterIdx) &&
0472 thisL != prevL) {
0473 ++nUL;
0474 prevL = thisL;
0475 }
0476 ch = hot_node.m_prev_idx;
0477 }
0478 return nUL;
0479 }
0480
0481 inline int TrackCand::nHitsByTypeEncoded(const TrackerInfo& trk_inf) const {
0482 int prevL = -1;
0483 bool prevStereo = false;
0484 int nh = nTotalHits();
0485 int ch = lastHitIdx_;
0486 int pix = 0, stereo = 0, mono = 0, matched = 0;
0487 int doubleStereo = -1;
0488 while (--nh >= 0) {
0489 const HoTNode& hot_node = m_comb_candidate->hot_node(ch);
0490 int thisL = hot_node.m_hot.layer;
0491 if (thisL >= 0 && (hot_node.m_hot.index >= 0 || hot_node.m_hot.index == Hit::kHitCCCFilterIdx)) {
0492 bool cStereo = trk_inf[thisL].is_stereo();
0493 if (trk_inf[thisL].is_pixel())
0494 ++pix;
0495 else if (cStereo) {
0496 ++stereo;
0497 if (thisL == prevL)
0498 doubleStereo = thisL;
0499 } else {
0500
0501 ++mono;
0502 if (prevStereo && thisL == prevL - 1)
0503 ++matched;
0504 else if (thisL == prevL && thisL == doubleStereo - 1)
0505 ++matched;
0506 }
0507 prevL = thisL;
0508 prevStereo = cStereo;
0509 }
0510 ch = hot_node.m_prev_idx;
0511 }
0512 return pix + 100 * stereo + 10000 * mono + 1000000 * matched;
0513 }
0514
0515 inline int TrackCand::nLayersByTypeEncoded(const TrackerInfo& trk_inf) const {
0516 int prevL = -1;
0517 bool prevStereo = false;
0518 int nh = nTotalHits();
0519 int ch = lastHitIdx_;
0520 int pix = 0, stereo = 0, mono = 0, matched = 0;
0521 while (--nh >= 0) {
0522 const HoTNode& hot_node = m_comb_candidate->hot_node(ch);
0523 int thisL = hot_node.m_hot.layer;
0524 if (thisL >= 0 && (hot_node.m_hot.index >= 0 || hot_node.m_hot.index == Hit::kHitCCCFilterIdx) &&
0525 thisL != prevL) {
0526 bool cStereo = trk_inf[thisL].is_stereo();
0527 if (trk_inf[thisL].is_pixel())
0528 ++pix;
0529 else if (cStereo)
0530 ++stereo;
0531 else {
0532
0533 ++mono;
0534 if (prevStereo && thisL == prevL - 1)
0535 ++matched;
0536 }
0537 prevL = thisL;
0538 prevStereo = cStereo;
0539 }
0540 ch = hot_node.m_prev_idx;
0541 }
0542 return pix + 100 * stereo + 10000 * mono + 1000000 * matched;
0543 }
0544
0545 inline HoTNode& TrackCand::refLastHoTNode() { return m_comb_candidate->hot_node_nc(lastHitIdx_); }
0546
0547 inline const HoTNode& TrackCand::refLastHoTNode() const { return m_comb_candidate->hot_node(lastHitIdx_); }
0548
0549
0550
0551 inline void TrackCand::addHitIdx(int hitIdx, int hitLyr, float chi2) {
0552 lastHitIdx_ = m_comb_candidate->addHit({hitIdx, hitLyr}, chi2, lastHitIdx_);
0553
0554 if (hitIdx >= 0 || hitIdx == Hit::kHitCCCFilterIdx) {
0555 ++nFoundHits_;
0556 chi2_ += chi2;
0557 nInsideMinusOneHits_ += nTailMinusOneHits_;
0558 nTailMinusOneHits_ = 0;
0559 }
0560
0561 else {
0562 ++nMissingHits_;
0563 if (hitIdx == Hit::kHitMissIdx)
0564 ++nTailMinusOneHits_;
0565 }
0566 }
0567
0568 inline bool TrackCand::popOverlap() {
0569 auto popHitIdx = getLastHitIdx();
0570 auto popHitLyr = getLastHitLyr();
0571 auto popPrev = refLastHoTNode().m_prev_idx;
0572 auto popChi2 = refLastHoTNode().m_chi2;
0573
0574 if (lastHitIdx_ == 0 || popHitIdx < 0)
0575 return false;
0576 auto prevHitLyr = m_comb_candidate->hot(popPrev).layer;
0577 auto prevHitIdx = m_comb_candidate->hot(popPrev).index;
0578 if (popHitLyr != prevHitLyr || prevHitIdx < 0)
0579 return false;
0580 lastHitIdx_ = popPrev;
0581
0582 --nFoundHits_;
0583 chi2_ -= popChi2;
0584 --nOverlapHits_;
0585 return true;
0586 }
0587
0588
0589 class EventOfCombCandidates {
0590 public:
0591 EventOfCombCandidates(int size = 0) : m_cc_pool(), m_candidates() {}
0592
0593 void releaseMemory() {
0594 {
0595 std::vector<CombCandidate> tmp;
0596 m_candidates.swap(tmp);
0597 }
0598 m_capacity = 0;
0599 m_size = 0;
0600 m_n_seeds_inserted = 0;
0601 m_cc_pool.release();
0602 }
0603
0604 void reset(int new_capacity, int max_cands_per_seed, int expected_num_hots = 128) {
0605 m_cc_pool.reset(new_capacity * max_cands_per_seed);
0606 if (new_capacity > m_capacity) {
0607 CcAlloc<TrackCand> alloc(&m_cc_pool);
0608 std::vector<CombCandidate> tmp(new_capacity, alloc);
0609 m_candidates.swap(tmp);
0610 m_capacity = new_capacity;
0611 }
0612 for (int s = 0; s < new_capacity; ++s) {
0613 m_candidates[s].reset(max_cands_per_seed, expected_num_hots);
0614 }
0615 for (int s = new_capacity; s < m_capacity; ++s) {
0616 m_candidates[s].reset(0, 0);
0617 }
0618
0619 m_size = new_capacity;
0620 m_n_seeds_inserted = 0;
0621 }
0622
0623 void resizeAfterFiltering(int n_removed) {
0624 assert(n_removed <= m_size);
0625 m_size -= n_removed;
0626 m_n_seeds_inserted -= n_removed;
0627 }
0628
0629 void insertSeed(const Track& seed, int seed_idx, const track_score_func& score_func, int region, int pos) {
0630 assert(pos < m_size);
0631
0632 m_candidates[pos].importSeed(seed, seed_idx, score_func, region);
0633
0634 ++m_n_seeds_inserted;
0635 }
0636
0637 void compactifyHitStorageForBestCand(bool remove_seed_hits, int backward_fit_min_hits) {
0638 for (int i = 0; i < m_size; ++i)
0639 m_candidates[i].compactifyHitStorageForBestCand(remove_seed_hits, backward_fit_min_hits);
0640 }
0641
0642 void beginBkwSearch() {
0643 for (int i = 0; i < m_size; ++i)
0644 m_candidates[i].beginBkwSearch();
0645 m_cands_in_backward_rep = true;
0646 }
0647 void endBkwSearch() {
0648
0649 m_cands_in_backward_rep = false;
0650 }
0651
0652
0653 int size() const { return m_size; }
0654
0655 const CombCandidate& operator[](int i) const { return m_candidates[i]; }
0656 CombCandidate& operator[](int i) { return m_candidates[i]; }
0657 CombCandidate& cand(int i) { return m_candidates[i]; }
0658
0659 bool cands_in_backward_rep() const { return m_cands_in_backward_rep; }
0660
0661
0662 const std::vector<CombCandidate>& refCandidates() const { return m_candidates; }
0663 std::vector<CombCandidate>& refCandidates_nc() { return m_candidates; }
0664
0665 private:
0666 CcPool<TrackCand> m_cc_pool;
0667
0668 std::vector<CombCandidate> m_candidates;
0669
0670 int m_capacity = 0;
0671 int m_size = 0;
0672 int m_n_seeds_inserted = 0;
0673 bool m_cands_in_backward_rep = false;
0674 };
0675
0676 }
0677
0678 #endif