CMS 3D CMS Logo

Table.h
Go to the documentation of this file.
1 #ifndef FWCore_SOA_Table_h
2 #define FWCore_SOA_Table_h
3 // -*- C++ -*-
4 //
5 // Package: FWCore/SOA
6 // Class : Table
7 //
111 //
112 // Original Author: Chris Jones
113 // Created: Thu, 24 Aug 2017 16:18:05 GMT
114 //
115 
116 // system include files
117 #include <memory>
118 #include <tuple>
119 #include <array>
120 
121 // user include files
127 
128 //The following is needed for edm::Wrapper
130 
131 // forward declarations
132 
133 namespace edm {
134 namespace soa {
135 
136  template <typename... Args>
137  class Table {
138  public:
139  static constexpr const unsigned int kNColumns = sizeof...(Args);
140  using Layout = std::tuple<Args...>;
141  using const_iterator = ConstTableItr<Args...>;
142  using iterator = TableItr<Args...>;
143 
144  template <typename T, typename... CArgs>
145  Table(T const& iContainer, CArgs... iArgs): m_size(iContainer.size()) {
146  if constexpr(sizeof...(CArgs)==0) {
147  CtrFillerFromAOS::fill(m_values,iContainer);
148  } else {
149  CtrFillerFromContainers::fill(m_values,iContainer,std::forward<CArgs>(iArgs)...);
150  }
151  }
152 
153  template<typename T, typename... CArgs>
154  Table(T const& iContainer, ColumnFillers<CArgs...> iFiller) {
155  m_size = iContainer.size();
156  CtrFillerFromAOS::fillUsingFiller(iFiller,m_values, iContainer);
157  }
158 
159  Table( Table<Args...> const& iOther):m_size(iOther.m_size), m_values{{nullptr}} {
160  copyFromToWithResizeAll(m_size,iOther.m_values,m_values, std::make_index_sequence<sizeof...(Args)>{});
161  }
162 
163  Table( Table<Args...>&& iOther):m_size(0), m_values{{nullptr}} {
164  std::swap(m_size,iOther.m_size);
165  std::swap(m_values,iOther.m_values);
166  }
167 
168  Table() : m_size(0) {
169  }
170 
171  ~Table() {
172  dtr<0>(m_values);
173  }
174 
175  Table<Args...>& operator=(Table<Args...>&& iOther) {
176  Table<Args...> cp(std::move(iOther));
177  std::swap(m_size,cp.m_size);
178  std::swap(m_values, cp.m_values);
179  return *this;
180  }
181  Table<Args...>& operator=(Table<Args...> const& iOther) {
182  return operator=( Table<Args...>(iOther));
183  }
184 
185  unsigned int size() const {
186  return m_size;
187  }
188 
189  void resize(unsigned int iNewSize) {
190  if(m_size == iNewSize) { return;}
191  resizeFromTo<0>(m_size,iNewSize,m_values);
192  if(m_size < iNewSize) {
193  //initialize the extra values
194  resetStartingAt<0>(m_size, iNewSize,m_values);
195  }
196  m_size = iNewSize;
197  }
198 
199  template<typename U>
200  typename U::type const& get(size_t iRow) const {
201  return *(static_cast<typename U::type const*>(columnAddress<U>())+iRow);
202  }
203  template<typename U>
204  typename U::type & get(size_t iRow) {
205  return *(static_cast<typename U::type*>(columnAddress<U>())+iRow);
206  }
207 
208  template<typename U>
210  return ColumnValues<typename U::type>{static_cast<typename U::type*>(columnAddress<U>()), m_size};
211  }
212  template<typename U>
214  return MutableColumnValues<typename U::type>{static_cast<typename U::type*>(columnAddress<U>()), m_size};
215  }
216 
217  RowView<Args...> row(size_t iRow) const {
218  return *(begin()+iRow);
219  }
220  MutableRowView<Args...> row(size_t iRow) {
221  return *(begin()+iRow);
222  }
223 
225  std::array<void const*, sizeof...(Args)> t;
226  for(size_t i = 0; i<size();++i) { t[i] = m_values[i]; }
227  return const_iterator{t}; }
228  const_iterator end() const {
229  std::array<void const*, sizeof...(Args)> t;
230  for(size_t i = 0; i<size();++i) { t[i] = m_values[i]; }
231  return const_iterator{t,size()}; }
232 
234  iterator end() { return iterator{m_values,size()}; }
235 
236 
237  template<typename U>
238  void const * columnAddressWorkaround( U const*) const {
239  return columnAddress<U>();
240  }
241 
242  void const * columnAddressByIndex(unsigned int iIndex) const {
243  return m_values[iIndex];
244  }
245 
246  private:
247 
248  // Member data
249  unsigned int m_size = 0;
250  std::array<void *, sizeof...(Args)> m_values = {{nullptr}};
251 
252  template<typename U>
253  void const* columnAddress() const {
255  }
256 
257  template<typename U>
258  void * columnAddress() {
260  }
261 
262  //Recursive destructor handling
263  template <int I>
264  static void dtr(std::array<void*, sizeof...(Args)>& iArray) {
265  if constexpr(I<sizeof...(Args)) {
267  delete [] static_cast<Type*>(iArray[I]);
268  dtr<I+1>(iArray);
269  }
270  }
271 
272  //Construct the Table using a container per column
274  template<typename T, typename... U>
275  static size_t fill(std::array<void *, sizeof...(Args)>& oValues, T const& iContainer, U... iArgs) {
276  static_assert( sizeof...(Args) == sizeof...(U)+1, "Wrong number of arguments passed to Table constructor");
277  ctrFiller<0>(oValues,iContainer.size(), iContainer,std::forward<U>(iArgs)...);
278  return iContainer.size();
279  }
280  private:
281  template<int I, typename T, typename... U>
282  static void ctrFiller(std::array<void *, sizeof...(Args)>& oValues, size_t iSize, T const& iContainer, U... iU) {
283  assert(iContainer.size() == iSize);
285  Type * temp = new Type [iSize];
286  unsigned int index = 0;
287  for( auto const& v: iContainer) {
288  temp[index] = v;
289  ++index;
290  }
291  oValues[I] = temp;
292 
293  ctrFiller<I+1>(oValues, iSize, std::forward<U>(iU)... );
294  }
295 
296  template<int I>
297  static void ctrFiller(std::array<void *, sizeof...(Args)>& , size_t ) {}
298 
299  };
300 
301  //Construct the Table using one container with each entry representing a row
303  template<typename T>
304  static size_t fill(std::array<void *, sizeof...(Args)>& oValues, T const& iContainer) {
305  presize<0>(oValues,iContainer.size());
306  unsigned index=0;
307  for(auto&& item: iContainer) {
308  fillElement<0>(item,index,oValues);
309  ++index;
310  }
311  return iContainer.size();
312  }
313 
314  template<typename T, typename F>
315  static size_t fillUsingFiller(F& iFiller, std::array<void *, sizeof...(Args)>& oValues, T const& iContainer) {
316  presize<0>(oValues,iContainer.size());
317  unsigned index=0;
318  for(auto&& item: iContainer) {
319  fillElementUsingFiller<0>(iFiller, item,index,oValues);
320  ++index;
321  }
322  return iContainer.size();
323  }
324 
325 
326  private:
327  template<int I>
328  static void presize(std::array<void *, sizeof...(Args)>& oValues, size_t iSize) {
329  if constexpr(I<sizeof...(Args)) {
330  using Layout = std::tuple<Args...>;
332  oValues[I] = new Type[iSize];
333  presize<I+1>(oValues,iSize);
334  }
335  }
336 
337  template<int I, typename E>
338  static void fillElement(E const& iItem, size_t iIndex, std::array<void *, sizeof...(Args)>& oValues) {
339  if constexpr(I<sizeof...(Args)) {
340  using Layout = std::tuple<Args...>;
341  using ColumnType = typename std::tuple_element<I,Layout>::type;
342  using Type = typename ColumnType::type;
343  Type* pElement = static_cast<Type*>(oValues[I])+iIndex;
344  *pElement = value_for_column(iItem, static_cast<ColumnType*>(nullptr));
345  fillElement<I+1>(iItem, iIndex, oValues);
346  }
347  }
348 
349  template<int I, typename E, typename F>
350  static void fillElementUsingFiller(F& iFiller, E const& iItem, size_t iIndex, std::array<void *, sizeof...(Args)>& oValues) {
351  if constexpr(I<sizeof...(Args)) {
352  using Layout = std::tuple<Args...>;
353  using ColumnType = typename std::tuple_element<I,Layout>::type;
354  using Type = typename ColumnType::type;
355  Type* pElement = static_cast<Type*>(oValues[I])+iIndex;
356  *pElement = iFiller.value(iItem, static_cast<ColumnType*>(nullptr));
357  fillElementUsingFiller<I+1>(iFiller,iItem, iIndex, oValues);
358  }
359  }
360  };
361 
362  template<size_t... I>
363  static void copyFromToWithResizeAll(size_t iNElements, std::array<void *, sizeof...(Args)> const& iFrom, std::array<void*, sizeof...(Args)>& oTo,
364  std::index_sequence<I...>) {
365  (copyFromToWithResize<I>(iNElements, iFrom, oTo), ...);
366  }
367 
368  template<int I>
369  static void copyFromToWithResize(size_t iNElements, std::array<void *, sizeof...(Args)> const& iFrom, std::array<void*, sizeof...(Args)>& oTo) {
370  using Layout = std::tuple<Args...>;
372  Type* oldPtr = static_cast<Type*>(oTo[I]);
373  Type* ptr = new Type[iNElements];
374  oTo[I]=ptr;
375  std::copy(static_cast<Type const*>(iFrom[I]), static_cast<Type const*>(iFrom[I])+iNElements, ptr);
376  delete [] oldPtr;
377  }
378 
379  template<int I>
380  static void resizeFromTo(size_t iOldSize, size_t iNewSize, std::array<void *, sizeof...(Args)>& ioArray) {
381  if constexpr(I < sizeof...(Args)) {
382  using Layout = std::tuple<Args...>;
384  Type* oldPtr = static_cast<Type*>(ioArray[I]);
385  auto ptr = new Type[iNewSize];
386  auto nToCopy = std::min(iOldSize,iNewSize);
387  std::copy(static_cast<Type const*>(ioArray[I]), static_cast<Type const*>(ioArray[I])+nToCopy, ptr);
388  resizeFromTo<I+1>(iOldSize, iNewSize, ioArray );
389 
390  delete [] oldPtr;
391  ioArray[I]=ptr;
392  }
393  }
394 
395  template<int I>
396  static void resetStartingAt(size_t iStartIndex, size_t iEndIndex,std::array<void *, sizeof...(Args)>& ioArray) {
397  if constexpr(I < sizeof...(Args)) {
398  using Layout = std::tuple<Args...>;
400  auto ptr = static_cast<Type*>(ioArray[I]);
401  auto temp = Type{};
402  std::fill(ptr+iStartIndex, ptr+iEndIndex, temp);
403  resetStartingAt<I+1>(iStartIndex, iEndIndex, ioArray);
404  }
405  }
406 
407  };
408 
409 
410  /* Table Type Manipulation */
411  template <typename T1, typename T2> struct AddColumns;
412  template <typename... T1, typename... T2>
413  struct AddColumns<Table<T1...>, std::tuple<T2...>> {
414  using type = Table<T1...,T2...>;
415  };
416 
417  template <typename T1, typename T2>
419 
420  namespace impl {
421  template <typename LHS, typename E, typename RHS> struct RemoveColumnCheck;
422  template <typename LHS, typename E, typename T, typename... U>
423  struct RemoveColumnCheck<LHS, E, std::tuple<T,U...>> {
425  typename AddColumns<LHS,std::tuple<U...>>::type,
427  };
428 
429  template <typename LHS, typename E>
430  struct RemoveColumnCheck<LHS, E, std::tuple<>> {
431  using type = LHS;
432  };
433  }
434 
435  template <typename TABLE, typename E>
436  struct RemoveColumn {
437  using type = typename impl::RemoveColumnCheck<Table<>,E, typename TABLE::Layout>::type;
438  };
439 
440  template <typename TABLE, typename E>
442 
443  //This is used by edm::Wrapper
444  template< typename T> struct MakeTableExaminer;
445 
446  template<typename... Args>
447  struct MakeTableExaminer<Table<Args...>> {
448  static std::unique_ptr<TableExaminerBase> make(const Table<Args...>* iTable) {
449  return std::make_unique<TableExaminer<Table<Args...>> >(iTable);
450  }
451  };
452 }
453 }
454 #endif
type
Definition: HCALResponse.h:21
def copy(args, dbName)
static void copyFromToWithResizeAll(size_t iNElements, std::array< void *, sizeof...(Args)> const &iFrom, std::array< void *, sizeof...(Args)> &oTo, std::index_sequence< I... >)
Definition: Table.h:363
RowView< Args... > row(size_t iRow) const
Definition: Table.h:217
iterator begin()
Definition: Table.h:233
Table(Table< Args... > const &iOther)
Definition: Table.h:159
static void resetStartingAt(size_t iStartIndex, size_t iEndIndex, std::array< void *, sizeof...(Args)> &ioArray)
Definition: Table.h:396
void const * columnAddress() const
keep ROOT from trying to store this
Definition: Table.h:253
typename std::conditional< std::is_same< E, T >::value, typename AddColumns< LHS, std::tuple< U... >>::type, typename RemoveColumnCheck< typename AddColumns< LHS, std::tuple< T >>::type, E, std::tuple< U... >>::type >::type type
Definition: Table.h:426
static void fillElement(E const &iItem, size_t iIndex, std::array< void *, sizeof...(Args)> &oValues)
Definition: Table.h:338
void * columnAddress()
Definition: Table.h:258
#define constexpr
Table< Args... > & operator=(Table< Args... > &&iOther)
Definition: Table.h:175
MutableColumnValues< typename U::type > column()
Definition: Table.h:213
Table(T const &iContainer, CArgs...iArgs)
Definition: Table.h:145
Table(T const &iContainer, ColumnFillers< CArgs... > iFiller)
Definition: Table.h:154
static void copyFromToWithResize(size_t iNElements, std::array< void *, sizeof...(Args)> const &iFrom, std::array< void *, sizeof...(Args)> &oTo)
Definition: Table.h:369
void resize(unsigned int iNewSize)
Definition: Table.h:189
std::tuple< Args... > Layout
Definition: Table.h:140
void swap(edm::DataFrameContainer &lhs, edm::DataFrameContainer &rhs)
const std::complex< double > I
Definition: I.h:8
iterator end()
Definition: Table.h:234
static size_t fill(std::array< void *, sizeof...(Args)> &oValues, T const &iContainer, U...iArgs)
Definition: Table.h:275
T min(T a, T b)
Definition: MathUtil.h:58
void const * columnAddressWorkaround(U const *) const
Definition: Table.h:238
ColumnValues< typename U::type > column() const
Definition: Table.h:209
static size_t fill(std::array< void *, sizeof...(Args)> &oValues, T const &iContainer)
Definition: Table.h:304
unsigned int m_size
Definition: Table.h:249
static void dtr(std::array< void *, sizeof...(Args)> &iArray)
Definition: Table.h:264
std::array< void *, sizeof...(Args)> m_values
Definition: Table.h:250
const_iterator end() const
Definition: Table.h:228
Table< Args... > & operator=(Table< Args... > const &iOther)
Definition: Table.h:181
static void presize(std::array< void *, sizeof...(Args)> &oValues, size_t iSize)
Definition: Table.h:328
typename impl::RemoveColumnCheck< Table<>, E, typename TABLE::Layout >::type type
Definition: Table.h:437
static void resizeFromTo(size_t iOldSize, size_t iNewSize, std::array< void *, sizeof...(Args)> &ioArray)
Definition: Table.h:380
Table(Table< Args... > &&iOther)
Definition: Table.h:163
static void ctrFiller(std::array< void *, sizeof...(Args)> &, size_t)
Definition: Table.h:297
static size_t fillUsingFiller(F &iFiller, std::array< void *, sizeof...(Args)> &oValues, T const &iContainer)
Definition: Table.h:315
MutableRowView< Args... > row(size_t iRow)
Definition: Table.h:220
typename RemoveColumn< TABLE, E >::type RemoveColumn_t
Definition: Table.h:441
HLT enums.
void const * columnAddressByIndex(unsigned int iIndex) const
Definition: Table.h:242
static void ctrFiller(std::array< void *, sizeof...(Args)> &oValues, size_t iSize, T const &iContainer, U...iU)
Definition: Table.h:282
static std::unique_ptr< TableExaminerBase > make(const Table< Args... > *iTable)
Definition: Table.h:448
typename AddColumns< T1, T2 >::type AddColumns_t
Definition: Table.h:418
static uInt32 F(BLOWFISH_CTX *ctx, uInt32 x)
Definition: blowfish.cc:281
long double T
const_iterator begin() const
Definition: Table.h:224
static constexpr const unsigned int kNColumns
Definition: Table.h:139
static void fillElementUsingFiller(F &iFiller, E const &iItem, size_t iIndex, std::array< void *, sizeof...(Args)> &oValues)
Definition: Table.h:350
unsigned int size() const
Definition: Table.h:185
def move(src, dest)
Definition: eostools.py:511