Warning, file /include/Acts/Seeding/SeedFinderGbts.ipp was not indexed
or was modified since last indexation (in which case cross-reference links may be missing, inaccurate or erroneous).
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012 #include "Acts/Definitions/Algebra.hpp" //for M_PI
0013 #include "Acts/Geometry/Extent.hpp"
0014 #include "Acts/Seeding/SeedFilter.hpp"
0015 #include "Acts/Seeding/SeedFinder.hpp"
0016 #include "Acts/Seeding/SeedFinderGbtsConfig.hpp"
0017 #include "Acts/Seeding/SeedFinderUtils.hpp"
0018 #include "Acts/Utilities/BinningType.hpp"
0019
0020 #include <cmath>
0021 #include <fstream>
0022 #include <functional>
0023 #include <iostream>
0024 #include <list>
0025 #include <numeric>
0026 #include <type_traits>
0027 #include <vector>
0028
0029
0030
0031 namespace Acts {
0032
0033 template <typename external_spacepoint_t>
0034 SeedFinderGbts<external_spacepoint_t>::SeedFinderGbts(
0035 const SeedFinderGbtsConfig<external_spacepoint_t>& config,
0036 const GbtsGeometry<external_spacepoint_t>& gbtsGeo)
0037 : m_config(config) {
0038 m_storage = new GbtsDataStorage(gbtsGeo);
0039 }
0040
0041 template <typename external_spacepoint_t>
0042 SeedFinderGbts<external_spacepoint_t>::~SeedFinderGbts() {
0043 delete m_storage;
0044
0045 m_storage = nullptr;
0046 }
0047
0048
0049 template <typename external_spacepoint_t>
0050 void SeedFinderGbts<external_spacepoint_t>::loadSpacePoints(
0051 const std::vector<GbtsSP<external_spacepoint_t>>& gbtsSPvect) {
0052 for (const auto& gbtssp : gbtsSPvect) {
0053 bool is_Pixel = gbtssp.isPixel();
0054 if (!is_Pixel) {
0055 continue;
0056 }
0057 m_storage->addSpacePoint(gbtssp, (m_config.m_useClusterWidth > 0));
0058 }
0059
0060 m_config.m_phiSliceWidth = 2 * M_PI / m_config.m_nMaxPhiSlice;
0061
0062 m_storage->sortByPhi();
0063
0064 m_storage->generatePhiIndexing(1.5 * m_config.m_phiSliceWidth);
0065 }
0066
0067 template <typename external_spacepoint_t>
0068 void SeedFinderGbts<external_spacepoint_t>::runGbts_TrackFinder(
0069 std::vector<GbtsTrigTracklet<external_spacepoint_t>>& vTracks,
0070 const Acts::RoiDescriptor& roi,
0071 const Acts::GbtsGeometry<external_spacepoint_t>& gbtsGeo) {
0072 const float min_z0 = roi.zedMinus();
0073 const float max_z0 = roi.zedPlus();
0074 const float cut_zMinU = min_z0 + m_config.maxOuterRadius * roi.dzdrMinus();
0075 const float cut_zMaxU = max_z0 + m_config.maxOuterRadius * roi.dzdrPlus();
0076 float m_minR_squ = m_config.m_tripletPtMin * m_config.m_tripletPtMin /
0077 std::pow(m_config.ptCoeff, 2);
0078 float m_maxCurv = m_config.ptCoeff / m_config.m_tripletPtMin;
0079 const float maxKappa_high_eta = 0.8 / m_minR_squ;
0080 const float maxKappa_low_eta = 0.6 / m_minR_squ;
0081
0082
0083
0084 int currentStage = 0;
0085
0086 const Acts::GbtsConnector& connector = *(gbtsGeo.connector());
0087
0088 std::vector<Acts::GbtsEdge<external_spacepoint_t>> edgeStorage;
0089
0090 edgeStorage.reserve(m_config.MaxEdges);
0091
0092 int nEdges = 0;
0093
0094 for (std::map<int, std::vector<GbtsConnector::LayerGroup>>::const_iterator
0095 it = connector.m_layerGroups.begin();
0096 it != connector.m_layerGroups.end(); ++it, currentStage++) {
0097
0098
0099 for (const auto& layerGroup : (*it).second) {
0100 unsigned int dst = layerGroup.m_dst;
0101
0102 const GbtsLayer<external_spacepoint_t>* pL1 =
0103 gbtsGeo.getGbtsLayerByKey(dst);
0104
0105 if (pL1 == nullptr) {
0106 continue;
0107 }
0108
0109 for (const auto& conn :
0110 layerGroup.m_sources) {
0111
0112 unsigned int src = conn->m_src;
0113
0114 const GbtsLayer<external_spacepoint_t>* pL2 =
0115 gbtsGeo.getGbtsLayerByKey(src);
0116
0117 if (pL2 == nullptr) {
0118 continue;
0119 }
0120 int nDstBins = pL1->m_bins.size();
0121 int nSrcBins = pL2->m_bins.size();
0122
0123 for (int b1 = 0; b1 < nDstBins; b1++) {
0124
0125 const GbtsEtaBin<external_spacepoint_t>& B1 =
0126 m_storage->getEtaBin(pL1->m_bins.at(b1));
0127
0128 if (B1.empty()) {
0129 continue;
0130 }
0131
0132 float rb1 = pL1->getMinBinRadius(b1);
0133
0134
0135
0136 for (int b2 = 0; b2 < nSrcBins; b2++) {
0137
0138 if (m_config.m_useEtaBinning && (nSrcBins + nDstBins > 2)) {
0139 if (conn->m_binTable[b1 + b2 * nDstBins] != 1) {
0140 continue;
0141 }
0142 }
0143
0144 const GbtsEtaBin<external_spacepoint_t>& B2 =
0145 m_storage->getEtaBin(pL2->m_bins.at(b2));
0146
0147 if (B2.empty()) {
0148 continue;
0149 }
0150
0151 float rb2 = pL2->getMaxBinRadius(b2);
0152
0153
0154
0155 float deltaPhi =
0156 0.5f *
0157 m_config
0158 .m_phiSliceWidth;
0159
0160 if (m_config.m_useEtaBinning) {
0161 deltaPhi = 0.001f + m_maxCurv * std::fabs(rb2 - rb1);
0162 }
0163
0164 unsigned int first_it = 0;
0165 for (typename std::vector<
0166 GbtsNode<external_spacepoint_t>*>::const_iterator n1It =
0167 B1.m_vn.begin();
0168 n1It != B1.m_vn.end(); ++n1It) {
0169
0170 GbtsNode<external_spacepoint_t>* n1 = (*n1It);
0171
0172 if (n1->m_in.size() >= MAX_SEG_PER_NODE) {
0173 continue;
0174 }
0175
0176 float r1 = n1->m_spGbts.SP->r();
0177 float x1 = n1->m_spGbts.SP->x();
0178 float y1 = n1->m_spGbts.SP->y();
0179 float z1 = n1->m_spGbts.SP->z();
0180 float phi1 = std::atan(x1 / y1);
0181
0182 float minPhi = phi1 - deltaPhi;
0183 float maxPhi = phi1 + deltaPhi;
0184
0185 for (unsigned int n2PhiIdx = first_it;
0186 n2PhiIdx < B2.m_vPhiNodes.size();
0187 n2PhiIdx++) {
0188
0189 float phi2 = B2.m_vPhiNodes.at(n2PhiIdx).first;
0190
0191 if (phi2 < minPhi) {
0192 first_it = n2PhiIdx;
0193 continue;
0194 }
0195 if (phi2 > maxPhi) {
0196 break;
0197 }
0198
0199 GbtsNode<external_spacepoint_t>* n2 =
0200 B2.m_vn.at(B2.m_vPhiNodes.at(n2PhiIdx).second);
0201
0202 if (n2->m_out.size() >= MAX_SEG_PER_NODE) {
0203 continue;
0204 }
0205 if (n2->isFull()) {
0206 continue;
0207 }
0208
0209 float r2 = n2->m_spGbts.SP->r();
0210
0211 float dr = r2 - r1;
0212
0213 if (dr < m_config.m_minDeltaRadius) {
0214 continue;
0215 }
0216
0217 float z2 = n2->m_spGbts.SP->z();
0218
0219 float dz = z2 - z1;
0220 float tau = dz / dr;
0221 float ftau = std::fabs(tau);
0222 if (ftau > 36.0) {
0223 continue;
0224 }
0225
0226 if (ftau < n1->m_minCutOnTau) {
0227 continue;
0228 }
0229 if (ftau < n2->m_minCutOnTau) {
0230 continue;
0231 }
0232 if (ftau > n1->m_maxCutOnTau) {
0233 continue;
0234 }
0235 if (ftau > n2->m_maxCutOnTau) {
0236 continue;
0237 }
0238
0239 if (m_config.m_doubletFilterRZ) {
0240 float z0 = z1 - r1 * tau;
0241
0242 if (z0 < min_z0 || z0 > max_z0) {
0243 continue;
0244 }
0245
0246 float zouter = z0 + m_config.maxOuterRadius * tau;
0247
0248 if (zouter < cut_zMinU || zouter > cut_zMaxU) {
0249 continue;
0250 }
0251 }
0252
0253 float dx = n2->m_spGbts.SP->x() - x1;
0254 float dy = n2->m_spGbts.SP->y() - y1;
0255
0256 float L2 = 1 / (dx * dx + dy * dy);
0257
0258 float D =
0259 (n2->m_spGbts.SP->y() * x1 - y1 * n2->m_spGbts.SP->x()) /
0260 (r1 * r2);
0261
0262 float kappa = D * D * L2;
0263
0264 if (ftau < 4.0) {
0265 if (kappa > maxKappa_low_eta) {
0266 continue;
0267 }
0268
0269 } else {
0270 if (kappa > maxKappa_high_eta) {
0271 continue;
0272 }
0273 }
0274
0275
0276
0277 float exp_eta = std::sqrt(1 + tau * tau) - tau;
0278
0279 bool isGood =
0280 n2->m_in.size() <=
0281 2;
0282
0283 if (!isGood) {
0284 float uat_1 = 1.0f / exp_eta;
0285
0286 for (const auto& n2_in_idx : n2->m_in) {
0287 float tau2 = edgeStorage.at(n2_in_idx).m_p[0];
0288 float tau_ratio = tau2 * uat_1 - 1.0f;
0289
0290 if (std::fabs(tau_ratio) >
0291 m_config.cut_tau_ratio_max) {
0292
0293 continue;
0294 }
0295 isGood = true;
0296 break;
0297 }
0298 }
0299 if (!isGood) {
0300 continue;
0301 }
0302
0303 float curv = D * std::sqrt(L2);
0304 float dPhi2 = std::asin(curv * r2);
0305 float dPhi1 = std::asin(curv * r1);
0306
0307 if (nEdges < m_config.MaxEdges) {
0308 edgeStorage.emplace_back(n1, n2, exp_eta, curv, phi1 + dPhi1,
0309 phi2 + dPhi2);
0310
0311 n1->addIn(nEdges);
0312 n2->addOut(nEdges);
0313
0314 nEdges++;
0315 }
0316 }
0317 }
0318 }
0319 }
0320 }
0321 }
0322 }
0323
0324 std::vector<const GbtsNode<external_spacepoint_t>*> vNodes;
0325
0326 m_storage->getConnectingNodes(vNodes);
0327
0328 if (vNodes.empty()) {
0329 return;
0330 }
0331
0332 int nNodes = vNodes.size();
0333
0334 for (int nodeIdx = 0; nodeIdx < nNodes; nodeIdx++) {
0335 const GbtsNode<external_spacepoint_t>* pN = vNodes.at(nodeIdx);
0336
0337 std::vector<std::pair<float, int>> in_sort, out_sort;
0338 in_sort.resize(pN->m_in.size());
0339 out_sort.resize(pN->m_out.size());
0340
0341 for (int inIdx = 0; inIdx < static_cast<int>(pN->m_in.size()); inIdx++) {
0342 int inEdgeIdx = pN->m_in.at(inIdx);
0343 Acts::GbtsEdge<external_spacepoint_t>* pS = &(edgeStorage.at(inEdgeIdx));
0344 in_sort[inIdx].second = inEdgeIdx;
0345 in_sort[inIdx].first = pS->m_p[0];
0346 }
0347 for (int outIdx = 0; outIdx < static_cast<int>(pN->m_out.size());
0348 outIdx++) {
0349 int outEdgeIdx = pN->m_out.at(outIdx);
0350 Acts::GbtsEdge<external_spacepoint_t>* pS = &(edgeStorage.at(outEdgeIdx));
0351 out_sort[outIdx].second = outEdgeIdx;
0352 out_sort[outIdx].first = pS->m_p[0];
0353 }
0354
0355 std::sort(in_sort.begin(), in_sort.end());
0356 std::sort(out_sort.begin(), out_sort.end());
0357
0358 unsigned int last_out = 0;
0359
0360 for (unsigned int in_idx = 0; in_idx < in_sort.size();
0361 in_idx++) {
0362
0363 int inEdgeIdx = in_sort[in_idx].second;
0364
0365 Acts::GbtsEdge<external_spacepoint_t>* pS = &(edgeStorage.at(inEdgeIdx));
0366
0367 pS->m_nNei = 0;
0368 float tau1 = pS->m_p[0];
0369 float uat_1 = 1.0f / tau1;
0370 float curv1 = pS->m_p[1];
0371 float Phi1 = pS->m_p[2];
0372
0373 for (unsigned int out_idx = last_out; out_idx < out_sort.size();
0374 out_idx++) {
0375 int outEdgeIdx = out_sort[out_idx].second;
0376
0377 Acts::GbtsEdge<external_spacepoint_t>* pNS =
0378 &(edgeStorage.at(outEdgeIdx));
0379
0380 float tau2 = pNS->m_p[0];
0381 float tau_ratio = tau2 * uat_1 - 1.0f;
0382
0383 if (tau_ratio < -m_config.cut_tau_ratio_max) {
0384 last_out = out_idx;
0385 continue;
0386 }
0387 if (tau_ratio > m_config.cut_tau_ratio_max) {
0388 break;
0389 }
0390
0391 float dPhi = pNS->m_p[3] - Phi1;
0392
0393 if (dPhi < -M_PI) {
0394 dPhi += 2 * M_PI;
0395 } else if (dPhi > M_PI) {
0396 dPhi -= 2 * M_PI;
0397 }
0398
0399 if (dPhi < -m_config.cut_dphi_max || dPhi > m_config.cut_dphi_max) {
0400 continue;
0401 }
0402
0403 float curv2 = pNS->m_p[1];
0404 float dcurv = curv2 - curv1;
0405
0406 if (dcurv < -m_config.cut_dcurv_max || dcurv > m_config.cut_dcurv_max) {
0407 continue;
0408 }
0409
0410 pS->m_vNei[pS->m_nNei++] = outEdgeIdx;
0411 if (pS->m_nNei >= N_SEG_CONNS) {
0412 break;
0413 }
0414 }
0415 }
0416 }
0417
0418 const int maxIter = 15;
0419
0420 int maxLevel = 0;
0421
0422 int iter = 0;
0423
0424 std::vector<Acts::GbtsEdge<external_spacepoint_t>*> v_old;
0425
0426 for (int edgeIndex = 0; edgeIndex < nEdges; edgeIndex++) {
0427 Acts::GbtsEdge<external_spacepoint_t>* pS = &(edgeStorage.at(edgeIndex));
0428 if (pS->m_nNei == 0) {
0429 continue;
0430 }
0431 v_old.push_back(pS);
0432
0433 }
0434
0435 for (; iter < maxIter; iter++) {
0436
0437 std::vector<Acts::GbtsEdge<external_spacepoint_t>*> v_new;
0438 v_new.clear();
0439
0440 for (auto pS : v_old) {
0441 int next_level = pS->m_level;
0442
0443 for (int nIdx = 0; nIdx < pS->m_nNei; nIdx++) {
0444 unsigned int nextEdgeIdx = pS->m_vNei[nIdx];
0445
0446 Acts::GbtsEdge<external_spacepoint_t>* pN =
0447 &(edgeStorage.at(nextEdgeIdx));
0448
0449 if (pS->m_level == pN->m_level) {
0450 next_level = pS->m_level + 1;
0451 v_new.push_back(pS);
0452 break;
0453 }
0454 }
0455
0456 pS->m_next = next_level;
0457 }
0458
0459
0460 int nChanges = 0;
0461
0462 for (auto pS : v_new) {
0463 if (pS->m_next != pS->m_level) {
0464 nChanges++;
0465 pS->m_level = pS->m_next;
0466 if (maxLevel < pS->m_level) {
0467 maxLevel = pS->m_level;
0468 }
0469 }
0470 }
0471
0472 if (nChanges == 0) {
0473 break;
0474 }
0475
0476 v_old = std::move(v_new);
0477 v_new.clear();
0478 }
0479
0480 int minLevel = 3;
0481
0482 std::vector<Acts::GbtsEdge<external_spacepoint_t>*> vSeeds;
0483
0484 vSeeds.reserve(m_config.MaxEdges / 2);
0485
0486 for (int edgeIndex = 0; edgeIndex < nEdges; edgeIndex++) {
0487 Acts::GbtsEdge<external_spacepoint_t>* pS = &(edgeStorage.at(edgeIndex));
0488
0489 if (pS->m_level < minLevel) {
0490 continue;
0491 }
0492
0493 vSeeds.push_back(pS);
0494 }
0495
0496 m_triplets.clear();
0497
0498 std::sort(vSeeds.begin(), vSeeds.end(),
0499 typename Acts::GbtsEdge<external_spacepoint_t>::CompareLevel());
0500
0501 if (vSeeds.empty()) {
0502 return;
0503 }
0504
0505
0506
0507 GbtsTrackingFilter<external_spacepoint_t> tFilter(m_config.m_layerGeometry,
0508 edgeStorage);
0509
0510 for (auto pS : vSeeds) {
0511 if (pS->m_level == -1) {
0512 continue;
0513 }
0514
0515 GbtsEdgeState<external_spacepoint_t> rs(false);
0516
0517 tFilter.followTrack(pS, rs);
0518
0519 if (!rs.m_initialized) {
0520 continue;
0521 }
0522
0523 if (static_cast<int>(rs.m_vs.size()) < minLevel) {
0524 continue;
0525 }
0526
0527 std::vector<const GbtsSP<external_spacepoint_t>*> vSP;
0528
0529 for (typename std::vector<
0530 Acts::GbtsEdge<external_spacepoint_t>*>::reverse_iterator sIt =
0531 rs.m_vs.rbegin();
0532 sIt != rs.m_vs.rend(); ++sIt) {
0533 (*sIt)->m_level = -1;
0534
0535 if (sIt == rs.m_vs.rbegin()) {
0536 vSP.push_back(&(*sIt)->m_n1->m_spGbts);
0537 }
0538 vSP.push_back(&(*sIt)->m_n2->m_spGbts);
0539 }
0540
0541 if (vSP.size() < 3) {
0542 continue;
0543 }
0544
0545
0546
0547 unsigned int nTriplets = 0;
0548
0549 std::vector<TrigInDetTriplet<external_spacepoint_t>> output;
0550
0551 for (unsigned int idx_m = 1; idx_m < vSP.size() - 1; idx_m++) {
0552 const GbtsSP<external_spacepoint_t>& spM = *vSP.at(idx_m);
0553 const double pS_r = spM.SP->r();
0554 const double pS_x = spM.SP->x();
0555 const double pS_y = spM.SP->y();
0556 const double cosA = pS_x / pS_r;
0557 const double sinA = pS_y / pS_r;
0558
0559 for (unsigned int idx_o = idx_m + 1; idx_o < vSP.size(); idx_o++) {
0560 const GbtsSP<external_spacepoint_t>& spO = *vSP.at(idx_o);
0561
0562 double dx = spO.SP->x() - pS_x;
0563 double dy = spO.SP->y() - pS_y;
0564 double R2inv = 1.0 / (dx * dx + dy * dy);
0565 double xn = dx * cosA + dy * sinA;
0566 double yn = -dx * sinA + dy * cosA;
0567
0568 const double uo = xn * R2inv;
0569 const double vo = yn * R2inv;
0570
0571 for (unsigned int idx_i = 0; idx_i < idx_m; idx_i++) {
0572 const GbtsSP<external_spacepoint_t>& spI = *vSP.at(idx_i);
0573
0574 dx = spI.SP->x() - pS_x;
0575 dy = spI.SP->y() - pS_y;
0576 R2inv = 1.0 / (dx * dx + dy * dy);
0577
0578 xn = dx * cosA + dy * sinA;
0579 yn = -dx * sinA + dy * cosA;
0580
0581 const double ui = xn * R2inv;
0582 const double vi = yn * R2inv;
0583
0584
0585
0586 const double du = uo - ui;
0587 if (du == 0.0) {
0588 continue;
0589 }
0590 const double A = (vo - vi) / du;
0591 const double B = vi - A * ui;
0592 const double R_squ = (1 + A * A) / (B * B);
0593
0594 if (R_squ < m_minR_squ) {
0595 continue;
0596 }
0597
0598
0599
0600 const double fabs_d0 = std::abs(pS_r * (B * pS_r - A));
0601
0602 if (fabs_d0 > m_config.m_tripletD0Max) {
0603 continue;
0604 }
0605
0606
0607
0608
0609
0610
0611
0612
0613
0614
0615
0616
0617
0618
0619
0620 const double Q = fabs_d0 * fabs_d0;
0621
0622 output.emplace_back(spI, spM, spO, Q);
0623
0624 nTriplets++;
0625
0626 if (nTriplets >= m_config.m_maxTripletBufferLength) {
0627 break;
0628 }
0629 }
0630 if (nTriplets >= m_config.m_maxTripletBufferLength) {
0631 break;
0632 }
0633 }
0634 if (nTriplets >= m_config.m_maxTripletBufferLength) {
0635 break;
0636 }
0637 }
0638
0639 if (output.empty()) {
0640 continue;
0641 }
0642
0643 vTracks.emplace_back(vSP, output);
0644 }
0645 }
0646
0647 template <typename external_spacepoint_t>
0648 template <typename output_container_t>
0649 void SeedFinderGbts<external_spacepoint_t>::createSeeds(
0650 const Acts::RoiDescriptor& roi,
0651 const Acts::GbtsGeometry<external_spacepoint_t>& gbtsGeo,
0652 output_container_t& out_cont) {
0653 std::vector<GbtsTrigTracklet<external_spacepoint_t>>
0654 vTracks;
0655
0656 vTracks.reserve(5000);
0657
0658 runGbts_TrackFinder(vTracks, roi, gbtsGeo);
0659
0660 if (vTracks.empty()) {
0661 return;
0662 }
0663
0664 m_triplets.clear();
0665
0666 for (auto& track : vTracks) {
0667 for (auto& seed : track.m_seeds) {
0668
0669 float newQ = seed.Q();
0670 if (m_config.m_LRTmode) {
0671
0672 if (seed.s1().isPixel()) {
0673 newQ += 1000;
0674 }
0675 if (seed.s2().isPixel()) {
0676 newQ += 1000;
0677 }
0678 if (seed.s3().isPixel()) {
0679 newQ += 1000;
0680 }
0681 } else {
0682
0683
0684 if (seed.s3().isSCT()) {
0685 newQ += seed.s1().isSCT() ? 1000.0 : 10000.0;
0686 }
0687 }
0688 seed.Q(newQ);
0689 m_triplets.emplace_back(seed);
0690 }
0691 }
0692 vTracks.clear();
0693
0694 for (auto& triplet : m_triplets) {
0695 const external_spacepoint_t* S1 =
0696 triplet.s1().SP;
0697 const external_spacepoint_t* S2 = triplet.s2().SP;
0698 const external_spacepoint_t* S3 = triplet.s3().SP;
0699
0700
0701 float Vertex = 0;
0702 float Quality = triplet.Q();
0703
0704 out_cont.emplace_back(*S1, *S2, *S3, Vertex, Quality);
0705 }
0706 }
0707
0708
0709 template <typename external_spacepoint_t>
0710 std::vector<Seed<external_spacepoint_t>>
0711 SeedFinderGbts<external_spacepoint_t>::createSeeds(
0712 const Acts::RoiDescriptor& roi,
0713 const Acts::GbtsGeometry<external_spacepoint_t>& gbtsGeo) {
0714 std::vector<seed_t> r;
0715 createSeeds(roi, gbtsGeo, r);
0716 return r;
0717 }
0718
0719 }