Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-07-01 07:52:40

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/Utilities/Holders.hpp"
0012 
0013 #include <array>
0014 #include <vector>
0015 
0016 namespace Acts {
0017 
0018 template <typename T, class... Axes>
0019   requires(std::is_default_constructible_v<T> && !std::is_same_v<T, bool>)
0020 class Grid;
0021 
0022 /// @class GridGlobalIterator
0023 /// Grid iterator using the global position. This iterates on all
0024 /// the bins in the grid, including under- and over-flows
0025 /// @tparam T The type stored in the grid bins
0026 /// @tparam Axes ... The types of the axes in the grid
0027 template <typename T, class... Axes>
0028 class GridGlobalIterator {
0029  public:
0030   static constexpr std::size_t DIM = sizeof...(Axes);
0031 
0032   using iterator_category = std::random_access_iterator_tag;
0033   using value_type = T;
0034   using difference_type = std::ptrdiff_t;
0035   using pointer = value_type*;
0036   using reference = value_type&;
0037 
0038   /// @brief Default constructor
0039   GridGlobalIterator() = default;
0040   /// @brief Constructor taking ownership of the grid is not allowed
0041   /// @param [in] grid The grid
0042   /// @param [in] idx The global bin
0043   GridGlobalIterator(Grid<T, Axes...>&& grid, std::size_t idx) = delete;
0044   /// @brief Constructor not taking ownership of the grid
0045   /// @param [in] grid The grid
0046   /// @param [in] idx The global bin
0047   ///
0048   /// @pre Global bin index must be a valid index for the grid
0049   explicit GridGlobalIterator(const Grid<T, Axes...>& grid,
0050                               std::size_t idx = 0ul);
0051 
0052   /// @brief Copy constructor
0053   /// @param [in] other The GlobalBinIterator to be copied
0054   GridGlobalIterator(const GridGlobalIterator<T, Axes...>& other) = default;
0055   /// @brief Copy assignment
0056   /// @param [in] other The GlobalBinIterator to be copied
0057   /// @return The new global bin iterator
0058   GridGlobalIterator<T, Axes...>& operator=(
0059       const GridGlobalIterator<T, Axes...>& other) = default;
0060 
0061   /// @brief Move constructor
0062   /// @param [in] other The GlobalBinIterator to be moved
0063   ///
0064   /// This will invalidate the other GlobalBinIterator
0065   GridGlobalIterator(GridGlobalIterator<T, Axes...>&& other) noexcept;
0066   /// @brief Move assignment
0067   /// @param [in] other The GlobalBinIterator to be moved
0068   /// @return The new global bin iterator
0069   ///
0070   /// This will invalidate the other GlobalBinIterator
0071   GridGlobalIterator<T, Axes...>& operator=(
0072       GridGlobalIterator<T, Axes...>&& other) noexcept;
0073 
0074   /// @brief Default destructor
0075   ~GridGlobalIterator() = default;
0076 
0077   /// @brief Equality operator
0078   /// @param [in] other The other GridGlobalIterator to be compared against this one
0079   /// @return The result of the comparison
0080   bool operator==(const GridGlobalIterator<T, Axes...>& other) const;
0081   /// @brief Comparison (<=>) operator
0082   /// @param [in] other The other GridGlobalIterator to be compared against this one
0083   /// @return The result of the comparison
0084   auto operator<=>(const GridGlobalIterator<T, Axes...>& other) const;
0085 
0086   /// @brief Increment this iterator with an offset
0087   /// @param [in] offset The increment value
0088   /// @return The incremented iterator
0089   GridGlobalIterator<T, Axes...>& operator+=(const std::size_t offset);
0090   /// @brief Decrement this iterator with an offset
0091   /// @param [in] offset The decrement value
0092   /// @return The decremented iterator
0093   GridGlobalIterator<T, Axes...>& operator-=(const std::size_t offset);
0094   /// @brief Create incremented iterator
0095   /// @param [in] offset The increment value
0096   /// @return The incremented iterator
0097   GridGlobalIterator<T, Axes...> operator+(const std::size_t offset) const;
0098   /// @brief Create decremented iterator
0099   /// @param [in] offset The decrement value
0100   /// @return The decremented iterator
0101   GridGlobalIterator<T, Axes...> operator-(const std::size_t offset) const;
0102 
0103   /// @brief Distance between two GridGlobalIterators
0104   /// @param [in] other The other GridGlobalIterator
0105   /// @return The distance between the two iterators
0106   ///
0107   /// This will compute the distance by comparing the global positions in the
0108   /// two iterators
0109   ///
0110   /// @pre The two iterators must have the same grid
0111   difference_type operator-(const GridGlobalIterator<T, Axes...>& other) const;
0112   /// @brief Return stored value at given global position
0113   /// @return The stored value in the grid from that given global position
0114   const value_type& operator*() const;
0115 
0116   /// @brief Increment operator (pre)
0117   /// @return The global iterator after the increment
0118   ///
0119   /// This will increase the global position by one
0120   GridGlobalIterator<T, Axes...>& operator++();
0121   /// @brief Increment operator (post)
0122   /// @return The global iterator before the increment
0123   ///
0124   /// This will increase the global position by one
0125   GridGlobalIterator<T, Axes...> operator++(int);
0126 
0127   /// @brief Retrieve the global bin index
0128   /// @return The current global bin index in the grid
0129   std::size_t globalBinIndex() const;
0130   /// @brief Retrieve the local bins indices
0131   /// @return The current local bins indexed in the grid
0132   std::array<std::size_t, DIM> localBinsIndices() const;
0133 
0134  private:
0135   /// @brief The grid on which we are iterating
0136   ///
0137   /// The iterator never takes ownership of the grid. If the grid gets
0138   /// invalidated (e.g. in a move operation) we can get undefined behaviours
0139   /// if the iterator gets used after being invalidated
0140   detail::RefHolder<const Grid<T, Axes...>> m_grid{nullptr};
0141   /// @brief The iteration index, corresponding to the global bin in the grid
0142   std::size_t m_idx{0ul};
0143 };
0144 
0145 /// @class GridLocalIterator
0146 /// Grid iterator using the local position. This iterates on all
0147 /// local bins in the grid, and can exclude under- and over-flows
0148 /// Can also allow for custom navigation pattern along axes
0149 /// @tparam T The type stored in the grid bins
0150 /// @tparam Axes ... The types of the axes in the grid
0151 template <typename T, class... Axes>
0152 class GridLocalIterator {
0153  public:
0154   static constexpr std::size_t DIM = sizeof...(Axes);
0155 
0156   using iterator_category = std::bidirectional_iterator_tag;
0157   using value_type = T;
0158   using difference_type = std::ptrdiff_t;
0159   using pointer = value_type*;
0160   using reference = value_type&;
0161 
0162   /// @brief Default constructor
0163   GridLocalIterator() = default;
0164   /// @brief Constructor taking ownership of the grid is not allowed
0165   /// @param [in] grid The grid
0166   /// @param [in] indices The local position
0167   GridLocalIterator(Grid<T, Axes...>&& grid,
0168                     const std::array<std::size_t, DIM>& indices) = delete;
0169   /// @brief Constructor taking ownership of the grid is not allowed
0170   /// @param [in] grid The grid
0171   /// @param [in] indices The local position
0172   /// @param [in] navigation The custom navigation pattern for each axis
0173   ///
0174   /// @pre None of the navigation vectors is allowed to be an empty vector
0175   GridLocalIterator(
0176       Grid<T, Axes...>&& grid, const std::array<std::size_t, DIM>& indices,
0177       std::array<std::vector<std::size_t>, DIM> navigation) = delete;
0178   /// @brief Constructor
0179   /// @param [in] grid The grid
0180   /// @param [in] indices The local position
0181   ///
0182   /// @pre The local bins must be a valid local position in the grid
0183   GridLocalIterator(const Grid<T, Axes...>& grid,
0184                     const std::array<std::size_t, DIM>& indices);
0185   /// @brief Constructor with custom navigation pattern
0186   /// @param [in] grid The grid
0187   /// @param [in] indices The local position
0188   /// @param [in] navigation The custom navigation pattern for each axis
0189   ///
0190   /// @pre The local bins must be a valid local position in the grid.
0191   /// The navigation pattern must be consistent with the local bins (i.e. size
0192   /// <= num bins in the axis) in the grid and have no repetitions.
0193   ///
0194   /// @pre None of the navigation vectors is allowed to be an empty vector
0195   GridLocalIterator(const Grid<T, Axes...>& grid,
0196                     const std::array<std::size_t, DIM>& indices,
0197                     std::array<std::vector<std::size_t>, DIM> navigation);
0198 
0199   /// @brief Copy constructor
0200   /// @param [in] other The GridLocalIterator to be copied
0201   GridLocalIterator(const GridLocalIterator<T, Axes...>& other) = default;
0202   /// @brief Copy assignment operator
0203   /// @param [in] other The GridLocalIterator to be copied
0204   /// @return The copied GridLocalIterator
0205   GridLocalIterator<T, Axes...>& operator=(
0206       const GridLocalIterator<T, Axes...>& other) = default;
0207 
0208   /// @brief Move constructor
0209   /// @param [in] other The GridLocalIterator to be moved
0210   ///
0211   /// This will invalidate the other GridLocalIterator
0212   GridLocalIterator(GridLocalIterator<T, Axes...>&& other) noexcept;
0213   /// @brief Move assignment operator
0214   /// @param [in] other The GridLocalIterator to be moved
0215   /// @return The moved GridLocalIterator
0216   ///
0217   /// This will invalidate the other GridLocalIterator
0218   GridLocalIterator<T, Axes...>& operator=(
0219       GridLocalIterator<T, Axes...>&& other) noexcept;
0220 
0221   /// @brief Default destructor
0222   ~GridLocalIterator() = default;
0223 
0224   /// @brief Equality operator
0225   /// @param [in] other The other GridLocalIterator to be compared against this one
0226   /// @return The result of the comparison
0227   bool operator==(const GridLocalIterator<T, Axes...>& other) const;
0228 
0229   /// @brief Return stored value at given local position
0230   /// @return The stored value in the grid from that given local position
0231   const value_type& operator*() const;
0232 
0233   /// @brief Increment operator (pre)
0234   /// @return The local iterator after the increment
0235   ///
0236   /// This will increase the local position by one
0237   GridLocalIterator<T, Axes...>& operator++();
0238   /// @brief Increment operator (post)
0239   /// @return The local iterator before the increment
0240   ///
0241   /// This will increase the local position by one
0242   GridLocalIterator<T, Axes...> operator++(int);
0243 
0244   /// @brief Retrieve the global bin index
0245   /// @return The current global bin index in the grid
0246   std::size_t globalBinIndex() const;
0247   /// @brief Retrieve the local position
0248   /// @return The current local position in the grid
0249   std::array<std::size_t, DIM> localBinsIndices() const;
0250 
0251  private:
0252   /// @brief Increment the local position
0253   /// @tparam N Current dimension
0254   template <std::size_t N>
0255   void increment();
0256 
0257  private:
0258   /// @brief The grid on which we are iterating
0259   ///
0260   /// The iterator never takes ownership of the grid. If the grid gets
0261   /// invalidated (e.g. in a move operation) we can get undefined behaviours
0262   /// if the iterator gets used after being invalidated
0263   detail::RefHolder<const Grid<T, Axes...>> m_grid{nullptr};
0264   /// @brief The maximum number of local bins in the grid. This does not include
0265   /// under- and over-flow bins
0266   std::array<std::size_t, DIM> m_numLocalBins{};
0267   /// @brief The current iteration position.
0268   ///
0269   /// This represent the position in the navigation pattern.
0270   /// For each axis, the current index goes from 0ul to the size of the
0271   /// corresponding navigation
0272   ///
0273   /// The local position in the gris is then obtained, for each axis i,
0274   /// via m_navigationIndex[m_currentIndex[i]]
0275   std::array<std::size_t, DIM> m_currentIndex{};
0276   /// @brief The custom navigation pattern in the grid
0277   ///
0278   /// This allows users to define any custom iteration sequence in all the
0279   /// different axes of the grid. If nothing is defined by the user, then
0280   /// a std::iota is used as the default starting with the 1ul bin (0ul) is
0281   /// the under-flow in the axis
0282   std::array<std::vector<std::size_t>, DIM> m_navigationIndex{};
0283 };
0284 
0285 template <typename T, class... Axes>
0286 GridGlobalIterator(const Grid<T, Axes...>& grid,
0287                    std::size_t idx) -> GridGlobalIterator<T, Axes...>;
0288 
0289 }  // namespace Acts
0290 
0291 #include "Acts/Utilities/GridIterator.ipp"