Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-18 09:11:00

0001 // This file is part of the ACTS project.
0002 //
0003 // Copyright (C) 2016 CERN for the benefit of the ACTS project
0004 //
0005 // This Source Code Form is subject to the terms of the Mozilla Public
0006 // License, v. 2.0. If a copy of the MPL was not distributed with this
0007 // file, You can obtain one at https://mozilla.org/MPL/2.0/.
0008 
0009 #pragma once
0010 
0011 #include "Acts/Definitions/Algebra.hpp"
0012 
0013 #include <algorithm>
0014 #include <limits>
0015 #include <memory>
0016 #include <tuple>
0017 #include <utility>
0018 #include <vector>
0019 
0020 namespace Acts {
0021 /// @brief A description of a triplet candidate.
0022 /// @tparam external_space_point_t  The external spacepoint type.
0023 template <typename external_space_point_t>
0024 struct TripletCandidate {
0025   /// @brief Default Constructor
0026   TripletCandidate() = default;
0027 
0028   /// @brief Default Destructor
0029   ~TripletCandidate() = default;
0030 
0031   /// @brief constructor
0032   /// @param b The bottom space point
0033   /// @param m The middle space point
0034   /// @param t The top space point
0035   /// @param w The quality of the candidate
0036   /// @param z The z coordinate of the origin
0037   /// @param q Whether the candidate is high or low quality
0038   TripletCandidate(external_space_point_t& b, external_space_point_t& m,
0039                    external_space_point_t& t, float w, float z, bool q)
0040       : bottom(&b), middle(&m), top(&t), weight(w), zOrigin(z), isQuality(q) {}
0041 
0042   /// @brief Copy operations
0043   TripletCandidate(const TripletCandidate&) = default;
0044   TripletCandidate& operator=(const TripletCandidate&) = default;
0045 
0046   /// @brief Move operations
0047   TripletCandidate(TripletCandidate&& other) noexcept
0048       : bottom(std::exchange(other.bottom, nullptr)),
0049         middle(std::exchange(other.middle, nullptr)),
0050         top(std::exchange(other.top, nullptr)),
0051         weight(other.weight),
0052         zOrigin(other.zOrigin),
0053         isQuality(other.isQuality) {}
0054 
0055   TripletCandidate& operator=(TripletCandidate&& other) noexcept {
0056     bottom = std::exchange(other.bottom, nullptr);
0057     middle = std::exchange(other.middle, nullptr);
0058     top = std::exchange(other.top, nullptr);
0059     weight = other.weight;
0060     zOrigin = other.zOrigin;
0061     isQuality = other.isQuality;
0062     return *this;
0063   }
0064 
0065   external_space_point_t* bottom{nullptr};
0066   external_space_point_t* middle{nullptr};
0067   external_space_point_t* top{nullptr};
0068   float weight{0.};
0069   float zOrigin{0.};
0070   bool isQuality{false};
0071 };
0072 
0073 /// @class CandidatesForMiddleSp
0074 /// The CandidatesForMiddleSp collects the triplet candidates given a
0075 /// fixed middle spacepoint. It internally stores the triplet candidates
0076 /// keeping only those with the higher quality.
0077 ///
0078 /// @tparam external_space_point_t The external spacepoint type.
0079 
0080 template <typename external_space_point_t>
0081 concept SatisfyCandidateConcept = requires(external_space_point_t spacePoint) {
0082   { spacePoint.x() } -> std::convertible_to<float>;
0083   { spacePoint.y() } -> std::convertible_to<float>;
0084   { spacePoint.z() } -> std::convertible_to<float>;
0085 };
0086 
0087 template <SatisfyCandidateConcept external_space_point_t>
0088 class CandidatesForMiddleSp {
0089  public:
0090   using value_type = TripletCandidate<external_space_point_t>;
0091 
0092   /// @brief Setting maximum number of candidates to keep
0093   /// @param nLow Maximum number of candidates in the low-quality collection
0094   /// @param nHigh Maximum number of candidates in the high-quality collection
0095   void setMaxElements(std::size_t nLow, std::size_t nHigh);
0096 
0097   /// @brief Retrieve the triplet candidates, the resulting vector is already sorted,
0098   /// elements with higher quality first
0099   /// @returns Vector of triplet candidates
0100   std::vector<value_type> storage();
0101 
0102   /// @brief Adding a new triplet candidate to the collection, should it satisfy the
0103   /// selection criteria
0104   /// @param SpB Bottom space point
0105   /// @param SpM Medium space point
0106   /// @param SpT Top space point
0107   /// @param weight The quality of the triplet candidate
0108   /// @param zOrigin The z-coordinate of the origin
0109   /// @param isQuality Whether the triplet candidate is high or low quality
0110   /// @returns whether the triplet candidate has been added or not to the collection
0111   bool push(external_space_point_t& SpB, external_space_point_t& SpM,
0112             external_space_point_t& SpT, float weight, float zOrigin,
0113             bool isQuality);
0114 
0115   /// @brief Clear the internal storage
0116   void clear();
0117 
0118   /// @brief A function for sorting the triplet candidates from higher to lower quality
0119   /// @param i1 First triplet candidate
0120   /// @param i2 Second triplet candidate
0121   /// @returns The comparison result
0122   static bool descendingByQuality(const value_type& i1, const value_type& i2);
0123 
0124   /// @brief A function for sorting the triplet candidates from lower to higher quality
0125   /// @param i1 First triplet candidate
0126   /// @param i2 Second triplet candidate
0127   /// @returns The comparison result
0128   static bool ascendingByQuality(const value_type& i1, const value_type& i2);
0129 
0130   /// @brief Retrieve the number of Low quality candidates
0131   /// @returns The number of Low quality candidates
0132   std::size_t nLowQualityCandidates() const;
0133 
0134   /// @brief Retrieve the number of High quality candidates
0135   /// @returns The number of High quality candidates
0136   std::size_t nHighQualityCandidates() const;
0137 
0138  private:
0139   /// @brief dding a new triplet candidate to the collection, should it satisfy the
0140   /// selection criteria
0141   /// @param indices The collection into which the candidate should be stored
0142   /// @param n The current number of stored elements in the container
0143   /// @param nMax The maximum number of elements that can be stored in the container
0144   /// @param SpB The bottom space point
0145   /// @param SpM The middle space point
0146   /// @param SpT The top space point
0147   /// @param weight The quality of the triplet candidate
0148   /// @param zOrigin The z-coordinate of the origin
0149   /// @param isQuality Whether the triplet candidate is high or low quality
0150   /// @returns whether the triplet candidate has been added or not to the collection
0151   bool push(std::vector<std::size_t>& indices, std::size_t& n,
0152             const std::size_t nMax, external_space_point_t& SpB,
0153             external_space_point_t& SpM, external_space_point_t& SpT,
0154             float weight, float zOrigin, bool isQuality);
0155 
0156   /// @brief Check if an element exists in the collection. The element to be checked
0157   /// is supposed to be in the n position of the collection.
0158   /// @param n Index of the requested element
0159   /// @param maxSize Number of elements currently stored in the collection
0160   /// @returns Whether the element exists
0161   bool exists(const std::size_t n, const std::size_t maxSize) const;
0162 
0163   /// @brief Pop an element from a collection. The removal of the element from the collection
0164   /// does not imply its destruction. In fact, the number of stored elements is
0165   /// simply diminished by 1. The popped element is technically still available
0166   /// at the end of the collection.
0167   /// @param indices The collection
0168   /// @param currentSize The current number of element stored in the collection. The function will
0169   /// diminish this value by 1
0170   void pop(std::vector<std::size_t>& indices, std::size_t& currentSize);
0171 
0172   /// @brief Return the weight for a candidate
0173   /// @param indices The collection in which the element is stored
0174   /// @param n Index of the element in the collection
0175   /// @returns The weight of the candidate
0176   float weight(const std::vector<std::size_t>& indices, std::size_t n) const;
0177 
0178   /// @brief Move an element up in the min heap tree. The function checks whether the element's
0179   /// weight is lower of its parent's weight. If so, it swaps them. Reiterate
0180   /// the process until the element is in the correct position on the tree
0181   /// @param indices The collection
0182   /// @param n The index of the element to place in the correct position
0183   void bubbleup(std::vector<std::size_t>& indices, std::size_t n);
0184 
0185   /// @brief Move an element down in the min heap tree. The function checks whether the elements's
0186   /// weight is lower of its child's weights. If so, it swaps the element with
0187   /// the child with the lowest weight. Reiterate the process until the element
0188   /// is in the correct position on the tree
0189   /// @param indices The collection
0190   /// @param n The index of the element to place in the correct position
0191   /// @param actualSize The current number of elements stored in the collection
0192   void bubbledw(std::vector<std::size_t>& indices, std::size_t n,
0193                 std::size_t actualSize);
0194 
0195   /// @brief Adding a new triplet candidate to the collection. The function is called after the candidate has satisfied
0196   /// all the selection criteria
0197   /// @param indices The collection
0198   /// @param n Current number of stored elements in the collection
0199   /// @param nMax The maximum number of elements that can be stored in the collection
0200   /// @param element The element that must be added to the collection
0201   void addToCollection(std::vector<std::size_t>& indices, std::size_t& n,
0202                        const std::size_t nMax, value_type&& element);
0203 
0204  private:
0205   // sizes
0206   // m_maxSize* is the maximum size of the indices collections. These values
0207   // are set by the user once
0208   std::size_t m_maxSizeHigh{0};
0209   std::size_t m_maxSizeLow{0};
0210   // m_n_* is the current size of the indices collections [0, m_maxSize*).
0211   // These values are set internally by the class
0212   std::size_t m_nHigh{0};
0213   std::size_t m_nLow{0};
0214 
0215   // storage contains the collection of the candidates
0216   std::vector<value_type> m_storage{};
0217 
0218   // The following vectors store indexes to elements in the storage
0219   // They are sorted as a min heap tree, in which
0220   // Each node is lower than its children
0221   // Thus, it is guaranteed that the lower elements is at the front
0222   // Sorting criteria is the seed quality
0223   //
0224   // This is in effect faster sorted container - implementation with std::set
0225   // and std::priority_queue were tried and were found to be slower.
0226 
0227   // list of indexes of candidates with high quality in the storage
0228   std::vector<std::size_t> m_indicesHigh{};
0229   // list of indexes of candidates with low quality in the storage
0230   std::vector<std::size_t> m_indicesLow{};
0231 };
0232 
0233 }  // namespace Acts
0234 
0235 #include "Acts/Seeding/CandidatesForMiddleSp.ipp"