Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-09-18 08:41:41

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 <any>
0012 #include <cassert>
0013 #include <memory>
0014 #include <vector>
0015 
0016 namespace Acts::detail {
0017 
0018 /// Interface of the dynamic vector column used in the track container backend.
0019 /// The interface provides basic methods to retrieve the data in a type erase
0020 /// form. Further methods for memory pre-allocation and memory release are
0021 /// defined
0022 class DynamicColumnBase {
0023  public:
0024   virtual ~DynamicColumnBase() = default;
0025 
0026   /// Retrieve the stored data for the i-th proxy object stored in the container
0027   /// @param i: The index of the object within the container
0028   /// @return The stored data in a type-erased form for mutable access
0029   virtual std::any get(std::size_t i) = 0;
0030 
0031   /// Retrieve the stored data for the i-th proxy object stored in the container
0032   /// @param i: The index of the object within the container
0033   /// @return The stored data in a type-erased form for read access
0034   virtual std::any get(std::size_t i) const = 0;
0035 
0036   /// Allocate new memory for the proxy object held by the container
0037   virtual void add() = 0;
0038 
0039   /// Release all stored memory
0040   virtual void clear() = 0;
0041 
0042   /// Pre-reserve the memory for later allocation
0043   /// @param size: The number of memory blocks to allocate
0044   virtual void reserve(std::size_t size) = 0;
0045 
0046   /// Allocate memory for a given number of proxy objects
0047   /// @param size: The number of elements to be allocated
0048   virtual void resize(std::size_t size) = 0;
0049 
0050   /// Remove the memory associated with the i-th proxy object from the column
0051   /// @param i: The index of the object within the container
0052   virtual void erase(std::size_t i) = 0;
0053 
0054   /// The number of the currently allocated elements
0055   /// @return The size of the underlying storage
0056   virtual std::size_t size() const = 0;
0057 
0058   /// Copy the memory stored at the srcIdx of the passed DynamicColumn
0059   /// to the dstIdx of this instance
0060   /// @param dstIdx: Index of the memory slot of this instance
0061   ///                the copied information will be stored
0062   /// @param src: The source from where the memory can be copy
0063   /// @param srcIdx: Index at which element the memory to copy resides in src
0064   virtual void copyFrom(std::size_t dstIdx, const DynamicColumnBase& src,
0065                         std::size_t srcIdx) = 0;
0066 
0067   /// Copy some external data and store it in this instance
0068   /// @param dstIdx: Index if the memory slote where the passed
0069   ///                information will be stored
0070   /// @param srcPtr: Type-erased reference to the information to store
0071   virtual void copyFrom(std::size_t dstIdx, const std::any& srcPtr) = 0;
0072 
0073   /// Create a clone of this DynamicColumnBase instance
0074   /// @param empty: If toggled to true the content will not be
0075   ///               copied to the clone
0076   /// @returns A unique_ptr to a fresh DynamicColumnBase instance
0077   virtual std::unique_ptr<DynamicColumnBase> clone(
0078       bool empty = false) const = 0;
0079 };
0080 
0081 /// Actual implementation of the Column memory using a std::vector as backend.
0082 /// The template parameter can be anything which is default constrictible and
0083 /// copy assignable.
0084 /// @tparam T: Data type of the data to be stored by the column
0085 template <typename T>
0086 class DynamicColumn : public DynamicColumnBase {
0087  public:
0088   /// @copydoc DynamicColumnBase::get
0089   std::any get(std::size_t i) override {
0090     assert(i < m_vector.size() && "DynamicColumn out of bounds");
0091     return &m_vector[i];
0092   }
0093 
0094   /// @copydoc DynamicColumnBase::get
0095   std::any get(std::size_t i) const override {
0096     assert(i < m_vector.size() && "DynamicColumn out of bounds");
0097     return &m_vector[i];
0098   }
0099 
0100   /// @copydoc DynamicColumnBase::add
0101   void add() override { m_vector.emplace_back(); }
0102 
0103   /// @copydoc DynamicColumnBase::clear
0104   void clear() override { m_vector.clear(); }
0105 
0106   /// @copydoc DynamicColumnBase::resize
0107   void resize(std::size_t size) override { m_vector.resize(size); }
0108 
0109   /// @copydoc DynamicColumnBase::reserve
0110   void reserve(std::size_t size) override { m_vector.reserve(size); }
0111 
0112   /// @copydoc DynamicColumnBase::erase
0113   void erase(std::size_t i) override { m_vector.erase(m_vector.begin() + i); }
0114 
0115   /// @copydoc DynamicColumnBase::size
0116   std::size_t size() const override { return m_vector.size(); }
0117 
0118   /// @copydoc DynamicColumnBase::clone
0119   std::unique_ptr<DynamicColumnBase> clone(bool empty) const override {
0120     if (empty) {
0121       return std::make_unique<DynamicColumn<T>>();
0122     }
0123     return std::make_unique<DynamicColumn<T>>(*this);
0124   }
0125 
0126   /// @copydoc DynamicColumnBase::copyFrom
0127   void copyFrom(std::size_t dstIdx, const DynamicColumnBase& src,
0128                 std::size_t srcIdx) override {
0129     const auto* other = dynamic_cast<const DynamicColumn<T>*>(&src);
0130     assert(other != nullptr &&
0131            "Source column is not of same type as destination");
0132     m_vector.at(dstIdx) = other->m_vector.at(srcIdx);
0133   }
0134 
0135   /// @copydoc DynamicColumnBase::copyFrom
0136   void copyFrom(std::size_t dstIdx, const std::any& srcPtr) override {
0137     const auto* other = std::any_cast<const T*>(srcPtr);
0138     assert(other != nullptr &&
0139            "Source column is not of same type as destination");
0140     m_vector.at(dstIdx) = *other;
0141   }
0142 
0143  private:
0144   std::vector<T> m_vector;
0145 };
0146 
0147 /// Template specification to circumvent the flaws of the bool implementation
0148 /// of a std::vector.
0149 template <>
0150 class DynamicColumn<bool> : public DynamicColumnBase {
0151  public:
0152   /// @copydoc DynamicColumnBase::get
0153   std::any get(std::size_t i) override {
0154     assert(i < m_vector.size() && "DynamicColumn out of bounds");
0155     return &m_vector[i].value;
0156   }
0157 
0158   /// @copydoc DynamicColumnBase::get
0159   std::any get(std::size_t i) const override {
0160     assert(i < m_vector.size() && "DynamicColumn out of bounds");
0161     return &m_vector[i].value;
0162   }
0163 
0164   /// @copydoc DynamicColumnBase::add
0165   void add() override { m_vector.emplace_back(); }
0166 
0167   /// @copydoc DynamicColumnBase::reserve
0168   void reserve(std::size_t size) override { m_vector.reserve(size); }
0169 
0170   /// @copydoc DynamicColumnBase::resize
0171   void resize(std::size_t size) override { m_vector.resize(size); }
0172 
0173   /// @copydoc DynamicColumnBase::clear
0174   void clear() override { m_vector.clear(); }
0175 
0176   /// @copydoc DynamicColumnBase::erase
0177   void erase(std::size_t i) override { m_vector.erase(m_vector.begin() + i); }
0178 
0179   /// @copydoc DynamicColumnBase::size
0180   std::size_t size() const override { return m_vector.size(); }
0181 
0182   /// @copydoc DynamicColumnBase::clone
0183   std::unique_ptr<DynamicColumnBase> clone(bool empty) const override {
0184     if (empty) {
0185       return std::make_unique<DynamicColumn<bool>>();
0186     }
0187     return std::make_unique<DynamicColumn<bool>>(*this);
0188   }
0189 
0190   /// @copydoc DynamicColumnBase::copyFrom
0191   void copyFrom(std::size_t dstIdx, const DynamicColumnBase& src,
0192                 std::size_t srcIdx) override {
0193     const auto* other = dynamic_cast<const DynamicColumn<bool>*>(&src);
0194     assert(other != nullptr &&
0195            "Source column is not of same type as destination");
0196     m_vector.at(dstIdx) = other->m_vector.at(srcIdx);
0197   }
0198 
0199   /// @copydoc DynamicColumnBase::copyFrom
0200   void copyFrom(std::size_t dstIdx, const std::any& srcPtr) override {
0201     const auto* other = std::any_cast<const bool*>(srcPtr);
0202     assert(other != nullptr &&
0203            "Source column is not of same type as destination");
0204     m_vector.at(dstIdx).value = *other;
0205   }
0206 
0207  private:
0208   /// Auxiliary struct to wrap a boolean for use in a vector
0209   struct Wrapper {
0210     bool value{false};
0211   };
0212   std::vector<Wrapper> m_vector;
0213 };
0214 
0215 }  // namespace Acts::detail