ATLAS Offline Software
Loading...
Searching...
No Matches
MultiDimArray.h
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2020 CERN for the benefit of the ATLAS collaboration
3*/
4
5#ifndef MUONCALIBIDENTIFIER_MULTIDIMARRAY_H
6#define MUONCALIBIDENTIFIER_MULTIDIMARRAY_H
7
8/***************************************************************************
9 * Variable Multidimensional Array
10 * -----------------------------------------
11 *
12 * Author : Martin Woudstra
13 * Creation Date: 20 April 2004
14 * Last Update : 26 April 2005
15 ***************************************************************************/
16
17#include <iostream>
18#include <sstream>
19#include <limits.h>
20#include <float.h>
21
22// general default value calls default constructor
23
24template <class T, unsigned int N> class MultiDimArray;
25
28
29template <class T, unsigned int I>
39
42
43template<class T>
45public:
47 typedef typename T::ValueType ThisType;
49 static ThisType defaultThisType() { return T::defaultValue(); }
50 // no subtype
51};
52
55
56template<class T>
66
71
72template <class T, unsigned int N>
74public:
75 //
76 // several needed type definitions
77 //
80 typedef typename T::ValueType ValueType;
81 // default (invalid) values for subtypes
84 static const SubType& invalidSubType();
89 void clear();
90 /* Read-write access to subtype at index. If subtype at index does not exist,
91 it will be created. */
93 /* Read-only access to subtype at index. If subtype at index does not exist,
94 an invalid subtype is returned. */
95 const SubType& operator[]( int index ) const;
96 /* Minimum index of this field */
97 int minIndex() const;
98 /* Maximum index of this field */
99 int maxIndex() const;
101 unsigned int size() const;
104 unsigned int depth() const;
106 bool isInRange( int index ) const;
109 unsigned int totalSize() const;
111 unsigned int validSize() const;
113 void dump( std::ostream& os = std::cout ) const;
115 void dump( const std::string& prefix, std::ostream& os = std::cout ) const;
117 std::string dumpToString() const;
119 std::string dumpToString( const std::string& prefix ) const;
121 template< class K >
122 void dumpOneEntry( const K& indices, std::ostream& os = std::cout ) const;
124 template< class K >
125 std::string dumpOneEntryToString( const K& indices ) const;
126private:
129 unsigned int m_size;
131#ifdef MULTIDIMARRAY_DEBUG
132 static unsigned int s_objectCount;
133#endif
134};
135
136template <class T, unsigned int I>
140
141template <class T>
145
146template <class T, unsigned int N>
150
151template <class T, unsigned int N>
155
156template <class T, unsigned int N>
160
161template <class T, unsigned int N>
163 : m_data(0), m_minIndex(0), m_size(0)
164{
165#ifdef MULTIDIMARRAY_DEBUG
166 ++s_objectCount;
167 MsgStream log(Athena::getMessageSvc(),"MultiDimArray<T,N>");
168 log<<MSG::DEBUG<<"Creating MultiDimArray<" << N << ">" << " at " << this << " #objects: " << s_objectCount<<endmsg;
169#endif
170}
171
172template <class T, unsigned int N>
174#ifdef MULTIDIMARRAY_DEBUG
175 --s_objectCount;
176 MsgStream log(Athena::getMessageSvc(),"MultiDimArray<T,N>");
177 log<<MSG::DEBUG<<"Deleting MultiDimArray<" << N << ">" << " at " << this << " #objects: " << s_objectCount<<endmsg;
178#endif
179 delete[] m_data;
180}
181
182template <class T, unsigned int N>
184 : m_data(0), m_minIndex(0), m_size(0)
185{
186#ifdef MULTIDIMARRAY_DEBUG
187 ++s_objectCount;
188 MsgStream log(Athena::getMessageSvc(),"MultiDimArray<T,N>");
189 log<<MSG::DEBUG<<"Copying MultiDimArray<" << N << ">" << " at " << this << " #objects: " << s_objectCount<<endmsg;
190#endif
191 operator=( rhs );
192}
193
194template <class T, unsigned int N>
196 delete[] m_data;
197 m_data = 0;
198 m_size = 0;
199 m_minIndex = 0;
200}
201
202template <class T, unsigned int N>
204 return m_minIndex;
205}
206
207template <class T, unsigned int N>
209 return m_minIndex + m_size - 1;
210}
211
212template <class T, unsigned int N>
213inline unsigned int MultiDimArray<T,N>::size() const {
214 return m_size;
215}
216
217template <class T, unsigned int N>
218inline unsigned int MultiDimArray<T,N>::depth() const {
219 return N;
220}
221
222template <class T, unsigned int N>
223inline bool MultiDimArray<T,N>::isInRange( int index ) const {
224 return index >= minIndex() && index <= maxIndex();
225}
226
227template <class T, unsigned int N>
229#ifdef MULTIDIMARRAY_DEBUG
230 MsgStream log(Athena::getMessageSvc(),"MultiDimArray<T,N>");
231 log<<MSG::DEBUG<<"Assigning MultiDimArray<" << N << ">" << " to " << this << " from " << &rhs<<endmsg;
232#endif
233 // ensure equal data size
234 if ( m_size != rhs.m_size ) {
235 delete[] m_data;
236 m_size = rhs.m_size;
237 if ( m_size ) {
238 m_data = new SubType[m_size];
239 } else {
240 m_data = 0;
241 }
242 }
243 // copy the data
244 for ( unsigned int i = 0; i < m_size; ++i ) m_data[i] = rhs.m_data[i];
245 // set others
247
248 return *this;
249}
250
251template <class T, unsigned int N>
253 if ( !isInRange( index ) ) {
254 MsgStream log(Athena::getMessageSvc(),"MultiDimArray<T,N>");
255 log<<MSG::WARNING<<"MultiDimArray<" << N << ">::operator["<< index << "]" << " index out of range (" << minIndex() << "," << maxIndex() << ")"<<endmsg;
256 return s_invalidSubType;
257 }
258 return m_data[index - m_minIndex];
259}
260
261template <class T, unsigned int N>
263#ifdef MULTIDIMARRAY_DEBUG
264 MsgStream log(Athena::getMessageSvc(),"MultiDimArray<T,N>");
265#endif if ( !m_data ) {
267 m_size = 1;
268 m_data = new SubType[1];
270#ifdef MULTIDIMARRAY_DEBUG
271 log<<MSG::DEBUG<<"MultiDimArray<" << N << ">::operator["<< index << "]" << " at " << this << ":" << " new data array. size=" << m_size << " range=(" << minIndex() << "," << maxIndex() << ")"<<endmsg;
272#endif
273 } else if ( index > maxIndex() ) {
274 // add to vector at back
275 unsigned int oldSize = m_size;
276 int nAdd = index - maxIndex();
277 m_size += nAdd;
278 SubType* newData = new SubType[m_size];
279 // copy old data and set new data to invalid
280 unsigned int i = 0;
281 for ( ; i < oldSize; ++i ) newData[i] = m_data[i];
282 for ( ; i < m_size ; ++i ) newData[i] = s_invalidSubType;
283 delete[] m_data;
284 m_data = newData;
285#ifdef MULTIDIMARRAY_DEBUG
286 log<<MSG::DEBUG<<"MultiDimArray<" << N << ">::operator["<< index << "]" << " at " << this << ":" << " added " << nAdd << " at back. size=" << m_size << " range=(" << minIndex() << "," << maxIndex() << ")"<<endmsg;
287#endif
288 } else if ( index < minIndex() ) {
289 // add to vector at front
290 unsigned int nAdd = minIndex() - index;
291 m_size += nAdd;
292 SubType* newData = new SubType[m_size];
293 // copy old data and set new data to invalid
294 unsigned int i = 0;
295 for ( ; i < nAdd ; ++i ) newData[i] = s_invalidSubType;
296 for ( ; i < m_size; ++i ) newData[i] = m_data[i-nAdd];
297 delete[] m_data;
298 m_data = newData;
299 m_minIndex = index;
300#ifdef MULTIDIMARRAY_DEBUG
301 log<<MSG::DEBUG<<"MultiDimArray<" << N << ">::operator["<< index << "]" << " at " << this << ":" << " added " << nAdd << " at front. size=" << m_size << " range=(" << minIndex() << "," << maxIndex() << ")"<<endmsg;
302#endif
303 }
304 // return ref to indexed value
305 return m_data[index - m_minIndex];
306}
307
308
309template <class T, unsigned int N>
310static unsigned int totalSize( const MultiDimArray<T,N>& ht ) {
311 unsigned int nTotal = 0;
312 int idxMin = ht.minIndex();
313 int idxMax = ht.maxIndex();
314 for ( int idx = idxMin; idx <= idxMax; ++idx ) {
315 nTotal += totalSize( ht[idx] );
316 }
317 return nTotal;
318}
319
320template <class T, unsigned int N>
321static unsigned int validSize( const MultiDimArray<T,N>& ht ) {
322 unsigned int nTotal = 0;
323 int idxMin = ht.minIndex();
324 int idxMax = ht.maxIndex();
325 for ( int idx = idxMin; idx <= idxMax; ++idx ) {
326 nTotal += validSize( ht[idx] );
327 }
328 return nTotal;
329}
330
331template<class T>
332static unsigned int totalSize( const MultiDimArray<T,1>& ht ) {
333 return ht.size();
334}
335
336template<class T>
337static unsigned int validSize( const MultiDimArray<T,1>& ht ) {
338 unsigned int cnt = 0;
339 int idxMin = ht.minIndex();
340 int idxMax = ht.maxIndex();
341 for ( int idx = idxMin; idx <= idxMax; ++idx ) {
342 if ( ht[idx] != MultiDimArray<T,1>::invalidSubType() ) ++cnt;
343 }
344 return cnt;
345}
346
347template <class T, unsigned int N>
348inline unsigned int MultiDimArray<T,N>::totalSize() const {
349 return ::totalSize( *this );
350}
351
352template <class T, unsigned int N>
353inline unsigned int MultiDimArray<T,N>::validSize() const {
354 return ::validSize( *this );
355}
356
357template <class T, unsigned int N>
358void dump( const MultiDimArray<T,N>& idh, std::ostream& os = std::cout,
359 const std::string& prefix = "(" ) {
360 int idxMin = idh.minIndex();
361 int idxMax = idh.maxIndex();
362 for ( int idx = idxMin; idx <= idxMax; ++idx ) {
363 std::ostringstream oss;
364 oss << idx << ",";
365 dump( idh[idx], os, prefix + oss.str() );
366 }
367}
368
369template <class T>
370void dump( const MultiDimArray<T,1>& idh, std::ostream& os = std::cout,
371 const std::string& prefix = "(" ) {
372 int idxMin = idh.minIndex();
373 int idxMax = idh.maxIndex();
374 for ( int idx = idxMin; idx <= idxMax; ++idx ) {
375 os << prefix << idx << "): hash=" << idh[idx] << "\n";
376 }
377}
378
379template <class T, unsigned int N>
380inline void MultiDimArray<T,N>::dump( std::ostream& os ) const {
381 ::dump( *this, os );
382 os.flush();
383}
384
385template <class T, unsigned int N>
386inline void MultiDimArray<T,N>::dump( const std::string& prefix, std::ostream& os ) const {
387 ::dump( *this, os, prefix + "(" );
388 os.flush();
389}
390
391template <class T, unsigned int N>
392inline std::string MultiDimArray<T,N>::dumpToString() const {
393 std::ostringstream oss;
394 dump( oss );
395 return oss.str();
396}
397
398template <class T, unsigned int N>
399inline std::string MultiDimArray<T,N>::dumpToString( const std::string& prefix ) const {
400 std::ostringstream oss;
401 dump( prefix, oss );
402 return oss.str();
403}
404
405template <class T, unsigned int N, class K>
406void dumpOneEntry( const MultiDimArray<T,N>& idh, const K& indices,
407 std::ostream& os = std::cout, const std::string& prefix = "(" ) {
408 int idx = indices[N-1];
409 std::ostringstream oss;
410 oss << idx << ",";
411 dumpOneEntry( idh[idx], indices, os, prefix + oss.str() );
412}
413
414template<class T, class K>
415void dumpOneEntry( const MultiDimArray<T,1>& idh, const K& indices,
416 std::ostream& os = std::cout, const std::string& prefix = "(" ) {
417 int idx = indices[0];
418 os << prefix << idx << ")=" << idh[idx];
419}
420
421template <class T, unsigned int N>
422template <class K>
423inline void MultiDimArray<T,N>::dumpOneEntry( const K& indices, std::ostream& os ) const {
424 ::dumpOneEntry( *this, indices, os );
425}
426
427template <class T, unsigned int N>
428template< class K >
429std::string MultiDimArray<T,N>::dumpOneEntryToString( const K& indices ) const {
430 std::ostringstream oss;
431 dumpOneEntry( indices, oss );
432 return oss.str();
433}
434
435// to ease output
436template <class T, unsigned int N>
437std::ostream& operator<<( std::ostream& os, const MultiDimArray<T,N>& idh ) {
438 dump( idh, os );
439 return os;
440}
441
442//
443//static members
444//
445template <class T, unsigned int N>
447
448#ifdef MULTIDIMARRAY_DEBUG
449template <class T, unsigned int N>
450unsigned int MultiDimArray<T,N>::s_objectCount = 0;
451#endif
452
453
454
455
456#endif // MUONCALIBIDENTIFIER_MULTIDIMARRAY_H
#define endmsg
#define I(x, y, z)
Definition MD5.cxx:116
std::ostream & operator<<(std::ostream &os, const MultiDimArray< T, N > &idh)
static unsigned int validSize(const MultiDimArray< T, N > &ht)
MultiDimArray< T, N >::SubType MultiDimArray< T, N >::s_invalidSubType
static unsigned int totalSize(const MultiDimArray< T, N > &ht)
void dumpOneEntry(const MultiDimArray< T, N > &idh, const K &indices, std::ostream &os=std::cout, const std::string &prefix="(")
T::ValueType ThisType
define ThisType as T::ValueType
static ThisType defaultThisType()
MultiDimArrayTypes< T, 0 >::ThisType SubType
define the SubType as MultiDimArrayTypes<T,0>::ThisType
MultiDimArray< T, 1 > ThisType
define ThisType as a MultiDimArray<T,N> with N=1
General recursive subtyping trait.
MultiDimArray< T, I > ThisType
define ThisType as a MultiDimArray<T,I>
MultiDimArray< T, I-1 > SubType
define the SubType as MultiDimArrayTypes<T,I-1>
static ThisType defaultThisType()
Multi-dimensional array with a compile-time number of dimensions, and a run-time complete freedom ove...
static ValueType defaultValueType()
static const SubType & invalidSubType()
unsigned int totalSize() const
The total number of elements, including invalid (=default) holes, from this field downwards.
MultiDimArray(const MultiDimArray &)
void dump(const std::string &prefix, std::ostream &os=std::cout) const
Dump the complete table to an output stream, with an additional prefix before each line.
SubType & operator[](int index)
bool isInRange(int index) const
Check that an index is in the range of the this field.
unsigned int size() const
Size of this field.
void dump(std::ostream &os=std::cout) const
Dump the complete table to an output stream.
MultiDimArray & operator=(const MultiDimArray &)
int maxIndex() const
std::string dumpToString() const
Dump the complete table into a string.
void dumpOneEntry(const K &indices, std::ostream &os=std::cout) const
Dump one entry with given indices to an output stream.
const SubType & operator[](int index) const
MultiDimArray< T, N > ThisType
static SubType defaultSubType()
std::string dumpToString(const std::string &prefix) const
Dump the complete table into a string, with an additional prefix before each line.
int minIndex() const
MultiDimArrayTypes< T, N >::SubType SubType
unsigned int validSize() const
The total number of valid (=non-default) elements from this field downwards.
unsigned int depth() const
Depth of this field, i.e.
std::string dumpOneEntryToString(const K &indices) const
Dump one entry with given indices into a string.
IMessageSvc * getMessageSvc(bool quiet=false)
-event-from-file
Definition index.py:1