CMS 3D CMS Logo

propagate_const_array.h
Go to the documentation of this file.
1 #ifndef FWCore_Utilities_interface_propagate_const_array_h
2 #define FWCore_Utilities_interface_propagate_const_array_h
3 // -*- C++ -*-
4 //
5 // Package: FWCore/Utilities
6 // Class : propagate_const_array
7 // Description: Propagate const to array-like objects. Based on C++ experimental std::propagate_const.
8 // If used with an array of incomplete type, edm::propagate_const_array can only be declared
9 // and assigned to nullptr, but not assigned to an actual object or dereferenced.
10 
11 // system include files
12 #include <cstddef>
13 #include <type_traits>
14 #include <utility>
15 
16 // user include files
17 
18 // forward declarations
19 
20 namespace edm {
21  namespace impl {
22 
23  template <typename T>
24  concept ArrayAddressable = requires(T& a) { a[0]; } or std::is_array_v<T>;
25 
26  // for a type T, return the type of the return value of the subscript operator T[N]
27  template <typename T, typename = void, typename = void>
28  struct subscript_type {};
29 
30  // the specialisations for arrays allow supporting incomplete types
31  template <typename T>
32  struct subscript_type<T[]> {
33  using type = T;
34  };
35 
36  template <typename T, int N>
37  struct subscript_type<T[N]> {
38  using type = T;
39  };
40 
41  // for non-array types that implement the subscript operator[], a complete type is needed
42  template <typename T>
44  requires not std::is_array_v<T>;
46  }
47  struct subscript_type<T> {
48  using type = typename std::remove_reference<decltype(std::declval<T&>()[0])>::type;
49  };
50 
51  template <typename T>
53 
54  } // namespace impl
55 
56  template <impl::ArrayAddressable T>
58 
59  template <typename T>
61  template <typename T>
62  constexpr std::decay_t<T> const& get_underlying(propagate_const_array<T> const&);
63 
64  template <impl::ArrayAddressable T>
65  class propagate_const_array {
66  public:
67  friend constexpr std::decay_t<T>& get_underlying<T>(propagate_const_array<T>&);
68  friend constexpr std::decay_t<T> const& get_underlying<T>(propagate_const_array<T> const&);
69 
70  template <impl::ArrayAddressable U>
71  friend class propagate_const_array;
72 
74 
75  constexpr propagate_const_array() = default;
78  template <typename U>
79  constexpr propagate_const_array(U&& u) : m_value(std::forward<U>(u)) {}
80 
83 
84  template <typename U>
86  static_assert(std::is_convertible_v<std::decay_t<U>, std::decay_t<T>>,
87  "Cannot assign propagate_const_array<> of incompatible types");
88  m_value = other.m_value;
89  return *this;
90  }
91 
92  template <typename U>
94  m_value = std::forward<U>(u);
95  return *this;
96  }
97 
98  // ---------- const member functions ---------------------
99  constexpr element_type const* get() const { return &m_value[0]; }
100  constexpr element_type const& operator[](std::ptrdiff_t pos) const { return m_value[pos]; }
101 
102  constexpr operator element_type const*() const { return this->get(); }
103 
104  // ---------- member functions ---------------------------
105  constexpr element_type* get() { return &m_value[0]; }
106  constexpr element_type& operator[](std::ptrdiff_t pos) { return m_value[pos]; }
107 
108  constexpr operator element_type*() { return this->get(); }
109 
110  private:
111  // ---------- member data --------------------------------
112  std::decay_t<T> m_value;
113  };
114 
115  template <typename T>
117  return iP.m_value;
118  }
119 
120  template <typename T>
121  constexpr std::decay_t<T> const& get_underlying(propagate_const_array<T> const& iP) {
122  return iP.m_value;
123  }
124 
125 } // namespace edm
126 
127 #endif // FWCore_Utilities_interface_propagate_const_array_h
constexpr element_type & operator[](std::ptrdiff_t pos)
typename subscript_type< T >::type subscript_type_t
concept ArrayAddressable
constexpr propagate_const_array()=default
The Signals That Services Can Subscribe To This is based on ActivityRegistry and is current per Services can connect to the signals distributed by the ActivityRegistry in order to monitor the activity of the application Each possible callback has some defined which we here list in angle e< void, edm::EventID const &, edm::Timestamp const & > We also list in braces which AR_WATCH_USING_METHOD_ is used for those or
Definition: Activities.doc:12
constexpr propagate_const_array< T > & operator=(propagate_const_array &&)=default
#define N
Definition: blowfish.cc:9
typename std::remove_reference< decltype(std::declval< T & >()[0])>::type type
constexpr propagate_const_array & operator=(U &&u)
constexpr T & get_underlying(propagate_const< T > &)
HLT enums.
double a
Definition: hdecay.h:121
requires ArrayAddressable< T >
constexpr propagate_const_array & operator=(propagate_const_array< U > &other)
long double T
constexpr propagate_const_array(U &&u)
constexpr element_type const & operator[](std::ptrdiff_t pos) const