HOPS
HOPS class reference
MHO_NDArrayWrapper_1.hh
Go to the documentation of this file.
1 #ifndef MHO_NDArrayWrapper_1_HH__
2 #define MHO_NDArrayWrapper_1_HH__
3 
4 //this include file should not be used directly
5 #ifndef MHO_NDArrayWrapper_HH__
6  #error "Do not include MHO_NDArrayWrapper_1.hh directly; use MHO_NDArrayWrapper.hh instead."
7 #endif
8 
9 namespace hops
10 {
11 
15 template< typename XValueType > class MHO_NDArrayWrapper< XValueType, 1 >: public MHO_ExtensibleElement
16 {
17  public:
18  using value_type = XValueType;
19  using index_type = std::array< std::size_t, 1 >;
20  typedef std::integral_constant< std::size_t, 1 > rank;
21 
22  //constructors
23  MHO_NDArrayWrapper() { Construct(nullptr, nullptr); }; //empty constructor, to be configured later
24 
25  MHO_NDArrayWrapper(const std::size_t* dim) { Construct(nullptr, dim); }; //data is internally allocated
26 
27  MHO_NDArrayWrapper(XValueType* ptr, const std::size_t* dim)
28  {
29  Construct(ptr, dim);
30  }; //data is externally allocated/managed
31 
32  MHO_NDArrayWrapper(std::size_t dim) { Construct(nullptr, &dim); }; //data is internally allocated
33 
34  MHO_NDArrayWrapper(XValueType* ptr, std::size_t dim) { Construct(ptr, &dim); }; //data is externally allocated/managed
35 
37  {
38  Construct(nullptr, &(obj.fDims[0]));
39  std::copy(obj.fData.begin(), obj.fData.end(), fData.begin());
40  }
41 
42  //destructor
43  virtual ~MHO_NDArrayWrapper(){};
44 
45  //resize functions
52  virtual void Resize(const std::size_t* dim) { Construct(nullptr, dim); }
53 
60  void Resize(std::size_t dim) { Resize(&dim); }
61 
62  //set pointer to externally managed array with associated dimension
69  void CopyFromExternalData(XValueType* ptr, const std::size_t* dim) { Construct(ptr, dim); }
70 
71  //access to underlying raw array pointer
77  XValueType* GetData() { return fData.data(); };
78 
84  const XValueType* GetData() const { return fData.data(); };
85 
86  //get the total size of the array
92  std::size_t GetRank() const { return 1; }
93 
99  std::size_t GetSize() const { return fDims[0]; };
100 
101  //get the dimensions/shape of the array
107  const std::size_t* GetDimensions() const { return &(fDims[0]); }
108 
114  void GetDimensions(std::size_t* dim) const { dim[0] = fDims[0]; }
115 
121  index_type GetDimensionArray() const { return fDims; }
122 
123  std::size_t GetDimension(std::size_t idx) const
124  {
125  if(idx == 0)
126  {
127  return fDims[0];
128  }
129  else
130  {
131  throw std::out_of_range("MHO_NDArrayWrapper_1::GetDimension() index out of range.");
132  }
133  }
134 
135  //get element strides
136  const std::size_t* GetStrides() const { return &(fStrides[0]); }
137 
138  void GetStrides(std::size_t* strd) const { strd[0] = fStrides[0]; }
139 
140  index_type GetStrideArray() const { return fStrides; }
141 
142  std::size_t GetStride(std::size_t idx) const { return fStrides[0]; }
143 
144  //access operators
145 
146  //access operator () -- no bounds checking
147  inline XValueType& operator()(std::size_t idx) { return fData[idx]; }
148 
149  inline const XValueType& operator()(std::size_t idx) const { return fData[idx]; }
150 
151  //access via at() -- same as operator() but with bounds checking
152  inline XValueType& at(std::size_t idx) { return fData.at(idx); }
153 
154  inline const XValueType& at(std::size_t idx) const { return fData.at(idx); }
155 
156  //in 1-d case, operator[] is same as operator()
157  XValueType& operator[](std::size_t i) { return fData[i]; }
158 
159  const XValueType& operator[](std::size_t i) const { return fData[i]; }
160 
161  //assignment operator
163  {
164  if(this != &rhs)
165  {
166  Construct(nullptr, &(rhs.fDims[0]));
167  std::copy(rhs.fData.begin(), rhs.fData.end(), this->fData.begin());
168  }
169  return *this;
170  }
171 
172  //convenience functions
173  void SetArray(const XValueType& obj)
174  {
175  for(std::size_t i = 0; i < fDims[0]; i++)
176  {
177  fData[i] = obj;
178  }
179  }
180 
181  void ZeroArray() { std::fill(fData.begin(), fData.end(), XValueType{}); }
182 
183  //expensive copy (as opposed to the assignment operator,
184  //pointers to exernally managed memory are not transferred)
185  //but copied instead, inteally managed memory is also copied
186  virtual void Copy(const MHO_NDArrayWrapper& rhs)
187  {
188  if(this != &rhs)
189  {
190  Construct(nullptr, &(rhs.fDims[0]));
191  std::copy(rhs.fData.begin(), rhs.fData.end(), this->fData.begin());
192  }
193  }
194 
195  // //append the contents of the addition to the end of vector container
196  // virtual int Append(const MHO_NDArrayWrapper& addition)
197  // {
198  // if(this == &addition)
199  // {
200  // msg_error("containers", "cannot append 1d-array to itself." << eom);
201  // return 1;
202  // }
203  //
204  // XValueType* &(fData[0]);
205  // bool fExternallyManaged;
206  // std::vector< XValueType > fData; //used for internally managed data
207  // index_type fDims; //size of each dimension
208  // index_type fStrides; //strides between elements in each dimension
209  // mutable index_type fTmp; //temp index workspace
210  // std::size_t fDims[0]; //total size of array
211  //
212  // fData.reserve( fDims[0] + addition.fDims[0]);
213  // //in-case our re-allocation has triggered a move, we need to update the &(fData[0])
214  //
215  // if(addition.fExternallyManaged)
216  // {
217  // fData.insert(addition.end(), addition.begin(), addition.end());
218  //
219  // &(fData[0]) = &(fData[0]);
220  // fDims[0] = fData.size();
221  // fDims[0] = fDims[0];
222  // fStrides = 1;
223  // }
224  //
225  // Construct(nullptr, &(rhs.fDims[0]));
226  // if(fDims[0] != 0){std::copy(rhs.fData.begin(), rhs.fData.end(), this->fData.begin() );}
227  // return 0;
228  //
229  // }
230 
231  //linear offset into the array -- no real utility in 1-d case
232  std::size_t GetOffsetForIndices(const std::size_t* index) { return index[0]; }
233 
234  index_type GetIndicesForOffset(std::size_t offset)
235  {
236  index_type val;
237  val[0] = offset;
238  return val;
239  }
240 
241  //here mainly so table containers with rank 1 still work, in this case a sub-view just gets you a scalar
242  template< typename... XIndexTypeS >
243  typename std::enable_if< (sizeof...(XIndexTypeS) < 1),
244  MHO_NDArrayWrapper< XValueType, 1 - (sizeof...(XIndexTypeS)) > >::type
245  SubView(XIndexTypeS... idx)
246  {
247  std::array< std::size_t, sizeof...(XIndexTypeS) > leading_idx = {{static_cast< size_t >(idx)...}};
248  for(std::size_t i = 0; i < 1; i++)
249  {
250  fTmp[i] = 0;
251  }
252  for(std::size_t i = 0; i < leading_idx.size(); i++)
253  {
254  fTmp[i] = leading_idx[i];
255  }
256  std::size_t offset = MHO_NDArrayMath::OffsetFromRowMajorIndex< 1 >(&(fDims[0]), &(fTmp[0]));
257  std::array< std::size_t, 1 - (sizeof...(XIndexTypeS)) > dim;
258  for(std::size_t i = 0; i < dim.size(); i++)
259  {
260  dim[i] = fDims[i + (sizeof...(XIndexTypeS))];
261  }
262  return MHO_NDArrayWrapper< XValueType, 1 - (sizeof...(XIndexTypeS)) >(VPTR_AT(fData, offset), &(dim[0]));
263  }
264 
265  //this function is mainly here to allow for 1-d table containers, there's not much utility
266  //of a 'slice view' of a 1-d array (you just get the same array back...)
268  {
269  //just return a 1d array view of this 1-d array
270  return MHO_NDArrayView< XValueType, 1 >(fData.data(), &(fDims[0]), &(fStrides[0]));
271  }
272 
273  XValueType& ValueAt(const index_type& idx) { return fData[idx[0]]; }
274 
275  const XValueType& ValueAt(const index_type& idx) const { return fData[idx[0]]; }
276 
277  //in place multiplication by a scalar factor
278  template< typename T >
279  typename std::enable_if< std::is_same< XValueType, T >::value or std::is_integral< T >::value or
280  std::is_floating_point< T >::value,
281  MHO_NDArrayWrapper& >::type inline
282  operator*=(T aScalar)
283  {
284  std::size_t length = fData.size();
285  for(std::size_t i = 0; i < length; i++)
286  {
287  fData[i] *= aScalar;
288  }
289  return *this;
290  }
291 
292  //in place addition by a scalar amount
293  template< typename T >
294  typename std::enable_if< std::is_same< XValueType, T >::value or std::is_integral< T >::value or
295  std::is_floating_point< T >::value,
296  MHO_NDArrayWrapper& >::type inline
297  operator+=(T aScalar)
298  {
299  std::size_t length = fData.size();
300  for(std::size_t i = 0; i < length; i++)
301  {
302  fData[i] += aScalar;
303  }
304  return *this;
305  }
306 
307  //in place subraction by a scalar amount
308  template< typename T >
309  typename std::enable_if< std::is_same< XValueType, T >::value or std::is_integral< T >::value or
310  std::is_floating_point< T >::value,
311  MHO_NDArrayWrapper& >::type inline
312  operator-=(T aScalar)
313  {
314  std::size_t length = fData.size();
315  for(std::size_t i = 0; i < length; i++)
316  {
317  fData[i] -= aScalar;
318  }
319  return *this;
320  }
321 
322  //in place point-wise multiplication by another array
324  {
325  if(!HaveSameNumberOfElements(this, &anArray))
326  {
327  throw std::out_of_range("MHO_NDArrayWrapper::*= size mismatch.");
328  }
329  std::size_t length = fData.size();
330  for(std::size_t i = 0; i < length; i++)
331  {
332  fData[i] *= anArray.fData[i];
333  }
334  return *this;
335  }
336 
337  //in place point-wise addition by another array of the same type
339  {
340  if(!HaveSameNumberOfElements(this, &anArray))
341  {
342  throw std::out_of_range("MHO_NDArrayWrapper::+= size mismatch.");
343  }
344  std::size_t length = fData.size();
345  for(std::size_t i = 0; i < length; i++)
346  {
347  fData[i] += anArray.fData[i];
348  }
349  return *this;
350  }
351 
352  //in place point-wise subtraction of another array
354  {
355  if(!HaveSameNumberOfElements(this, &anArray))
356  {
357  throw std::out_of_range("MHO_NDArrayWrapper::-= size mismatch.");
358  }
359  std::size_t length = fData.size();
360  for(std::size_t i = 0; i < length; i++)
361  {
362  fData[i] -= anArray.fData[i];
363  }
364  return *this;
365  }
366 
367  private:
368  std::vector< XValueType > fData; //used for internally managed data
369  index_type fDims; //size of each dimension
370  index_type fStrides; //strides between elements in each dimension
371  mutable index_type fTmp; //temp index workspace
372 
373  void Construct(XValueType* ptr, const std::size_t* dim)
374  {
375  //default construction (empty)
376  fDims[0] = 0;
377  fStrides[0] = 0;
378  if(ptr == nullptr && dim == nullptr)
379  {
380  return;
381  }
382 
383  //dimensions known
384  if(dim != nullptr)
385  {
386  fDims[0] = dim[0];
387  }
388  fStrides[0] = 1;
389 
390  fData.resize(fDims[0]);
391  if(ptr != nullptr) //if given a ptr, copy in data from this location
392  {
393  std::copy(ptr, ptr + fData.size(), fData.begin());
394  //std::memcpy(&(fData[0]), ptr, fData.size() * sizeof(XValueType));
395  }
396  }
397 
398  //the iterator definitions //////////////////////////////////////////////////
399  public:
402 
405 
406  iterator begin() { return iterator(fData.data(), fData.data(), fData.size()); }
407 
408  iterator end() { return iterator(fData.data(), fData.data() + fData.size(), fData.size()); }
409 
410  iterator iterator_at(std::size_t offset)
411  {
412  return iterator(fData.data(), fData.data() + std::min(offset, fData.size()), fData.size());
413  }
414 
415  const_iterator cbegin() const { return const_iterator(fData.data(), fData.data(), fData.size()); }
416 
417  const_iterator cend() const { return const_iterator(fData.data(), fData.data() + fData.size(), fData.size()); }
418 
419  const_iterator citerator_at(std::size_t offset) const
420  {
421  return const_iterator(fData.data(), fData.data() + std::min(offset, fData.size()), fData.size());
422  }
423 
424  stride_iterator stride_begin(std::size_t stride)
425  {
426  return stride_iterator(fData.data(), fData.data(), fData.size(), stride);
427  }
428 
429  stride_iterator stride_end(std::size_t stride)
430  {
431  return stride_iterator(fData.data(), fData.data() + fData.size(), fData.size(), stride);
432  }
433 
434  stride_iterator stride_iterator_at(std::size_t offset, std::size_t stride)
435  {
436  return stride_iterator(fData.data(), fData.data() + std::min(offset, fData.size()), fData.size(), stride);
437  }
438 
439  const_stride_iterator cstride_begin(std::size_t stride) const
440  {
441  return const_stride_iterator(fData.data(), fData.data(), fData.size(), stride);
442  }
443 
444  const_stride_iterator cstride_end(std::size_t stride) const
445  {
446  return const_stride_iterator(fData.data(), fData.data() + fData.size(), fData.size(), stride);
447  }
448 
449  const_stride_iterator cstride_iterator_at(std::size_t offset, std::size_t stride) const
450  {
451  return const_stride_iterator(fData.data(), fData.data() + std::min(offset, fData.size()), fData.size(), stride);
452  }
453 };
454 
455 } // namespace hops
456 
457 #endif
Class MHO_BidirectionalConstIterator.
Definition: MHO_BidirectionalIterator.hh:144
Class MHO_BidirectionalConstStrideIterator.
Definition: MHO_BidirectionalStrideIterator.hh:139
Class MHO_BidirectionalIterator.
Definition: MHO_BidirectionalIterator.hh:22
Class MHO_BidirectionalStrideIterator.
Definition: MHO_BidirectionalStrideIterator.hh:22
Class MHO_ExtensibleElement.
Definition: MHO_ExtensibleElement.hh:60
MHO_NDArrayView is a class to represent a view (slice) of a n-dimensional array Thu 13 Aug 2020 02:53...
Definition: MHO_NDArrayView.hh:32
XValueType & at(std::size_t idx)
Definition: MHO_NDArrayWrapper_1.hh:152
std::enable_if< std::is_same< XValueType, T >::value or std::is_integral< T >::value or std::is_floating_point< T >::value, MHO_NDArrayWrapper & >::type operator-=(T aScalar)
Definition: MHO_NDArrayWrapper_1.hh:312
MHO_NDArrayWrapper & operator=(const MHO_NDArrayWrapper &rhs)
Definition: MHO_NDArrayWrapper_1.hh:162
XValueType & ValueAt(const index_type &idx)
Definition: MHO_NDArrayWrapper_1.hh:273
virtual ~MHO_NDArrayWrapper()
Definition: MHO_NDArrayWrapper_1.hh:43
MHO_NDArrayWrapper(std::size_t dim)
Definition: MHO_NDArrayWrapper_1.hh:32
XValueType & operator()(std::size_t idx)
Definition: MHO_NDArrayWrapper_1.hh:147
std::size_t GetStride(std::size_t idx) const
Definition: MHO_NDArrayWrapper_1.hh:142
const_stride_iterator cstride_end(std::size_t stride) const
Definition: MHO_NDArrayWrapper_1.hh:444
MHO_NDArrayWrapper(const std::size_t *dim)
Definition: MHO_NDArrayWrapper_1.hh:25
MHO_NDArrayWrapper & operator*=(const MHO_NDArrayWrapper &anArray)
Definition: MHO_NDArrayWrapper_1.hh:323
void ZeroArray()
Definition: MHO_NDArrayWrapper_1.hh:181
MHO_NDArrayWrapper(XValueType *ptr, std::size_t dim)
Definition: MHO_NDArrayWrapper_1.hh:34
MHO_NDArrayWrapper & operator-=(const MHO_NDArrayWrapper &anArray)
Definition: MHO_NDArrayWrapper_1.hh:353
XValueType * GetData()
Getter for data.
Definition: MHO_NDArrayWrapper_1.hh:77
index_type GetIndicesForOffset(std::size_t offset)
Definition: MHO_NDArrayWrapper_1.hh:234
stride_iterator stride_begin(std::size_t stride)
Definition: MHO_NDArrayWrapper_1.hh:424
void SetArray(const XValueType &obj)
Definition: MHO_NDArrayWrapper_1.hh:173
std::enable_if< std::is_same< XValueType, T >::value or std::is_integral< T >::value or std::is_floating_point< T >::value, MHO_NDArrayWrapper & >::type operator+=(T aScalar)
Definition: MHO_NDArrayWrapper_1.hh:297
std::size_t GetRank() const
Getter for rank.
Definition: MHO_NDArrayWrapper_1.hh:92
const XValueType & operator[](std::size_t i) const
Definition: MHO_NDArrayWrapper_1.hh:159
const_stride_iterator cstride_begin(std::size_t stride) const
Definition: MHO_NDArrayWrapper_1.hh:439
std::array< std::size_t, 1 > index_type
Definition: MHO_NDArrayWrapper_1.hh:19
const std::size_t * GetDimensions() const
Getter for dimensions.
Definition: MHO_NDArrayWrapper_1.hh:107
index_type GetDimensionArray() const
Getter for dimension array.
Definition: MHO_NDArrayWrapper_1.hh:121
virtual void Copy(const MHO_NDArrayWrapper &rhs)
Definition: MHO_NDArrayWrapper_1.hh:186
const std::size_t * GetStrides() const
Definition: MHO_NDArrayWrapper_1.hh:136
std::enable_if< std::is_same< XValueType, T >::value or std::is_integral< T >::value or std::is_floating_point< T >::value, MHO_NDArrayWrapper & >::type operator*=(T aScalar)
Definition: MHO_NDArrayWrapper_1.hh:282
const_stride_iterator cstride_iterator_at(std::size_t offset, std::size_t stride) const
Definition: MHO_NDArrayWrapper_1.hh:449
const XValueType & ValueAt(const index_type &idx) const
Definition: MHO_NDArrayWrapper_1.hh:275
MHO_NDArrayWrapper()
Definition: MHO_NDArrayWrapper_1.hh:23
const_iterator cend() const
Definition: MHO_NDArrayWrapper_1.hh:417
std::enable_if<(sizeof...(XIndexTypeS)< 1), MHO_NDArrayWrapper< XValueType, 1 -(sizeof...(XIndexTypeS)) > >::type SubView(XIndexTypeS... idx)
Definition: MHO_NDArrayWrapper_1.hh:245
const_iterator cbegin() const
Definition: MHO_NDArrayWrapper_1.hh:415
index_type GetStrideArray() const
Definition: MHO_NDArrayWrapper_1.hh:140
MHO_NDArrayWrapper(XValueType *ptr, const std::size_t *dim)
Definition: MHO_NDArrayWrapper_1.hh:27
MHO_NDArrayView< XValueType, 1 > SliceView(const char *)
Definition: MHO_NDArrayWrapper_1.hh:267
std::size_t GetDimension(std::size_t idx) const
Definition: MHO_NDArrayWrapper_1.hh:123
iterator end()
Definition: MHO_NDArrayWrapper_1.hh:408
void CopyFromExternalData(XValueType *ptr, const std::size_t *dim)
Setter for external data.
Definition: MHO_NDArrayWrapper_1.hh:69
stride_iterator stride_end(std::size_t stride)
Definition: MHO_NDArrayWrapper_1.hh:429
const XValueType * GetData() const
Getter for data.
Definition: MHO_NDArrayWrapper_1.hh:84
iterator begin()
Definition: MHO_NDArrayWrapper_1.hh:406
const XValueType & operator()(std::size_t idx) const
Definition: MHO_NDArrayWrapper_1.hh:149
std::size_t GetOffsetForIndices(const std::size_t *index)
Definition: MHO_NDArrayWrapper_1.hh:232
std::integral_constant< std::size_t, 1 > rank
Definition: MHO_NDArrayWrapper_1.hh:20
virtual void Resize(const std::size_t *dim)
Resize an externally managed array using provided dimensions.
Definition: MHO_NDArrayWrapper_1.hh:52
void Resize(std::size_t dim)
Sets dimensions for externally managed array.
Definition: MHO_NDArrayWrapper_1.hh:60
std::size_t GetSize() const
Getter for size.
Definition: MHO_NDArrayWrapper_1.hh:99
void GetStrides(std::size_t *strd) const
Definition: MHO_NDArrayWrapper_1.hh:138
XValueType value_type
Definition: MHO_NDArrayWrapper_1.hh:18
stride_iterator stride_iterator_at(std::size_t offset, std::size_t stride)
Definition: MHO_NDArrayWrapper_1.hh:434
XValueType & operator[](std::size_t i)
Definition: MHO_NDArrayWrapper_1.hh:157
iterator iterator_at(std::size_t offset)
Definition: MHO_NDArrayWrapper_1.hh:410
MHO_NDArrayWrapper(const MHO_NDArrayWrapper &obj)
Definition: MHO_NDArrayWrapper_1.hh:36
void GetDimensions(std::size_t *dim) const
Getter for dimensions.
Definition: MHO_NDArrayWrapper_1.hh:114
const_iterator citerator_at(std::size_t offset) const
Definition: MHO_NDArrayWrapper_1.hh:419
const XValueType & at(std::size_t idx) const
Definition: MHO_NDArrayWrapper_1.hh:154
MHO_NDArrayWrapper & operator+=(const MHO_NDArrayWrapper &anArray)
Definition: MHO_NDArrayWrapper_1.hh:338
Class MHO_NDArrayWrapper.
Definition: MHO_NDArrayWrapper.hh:42
MHO_BidirectionalConstIterator< XValueType > const_iterator
Definition: MHO_NDArrayWrapper.hh:622
MHO_BidirectionalStrideIterator< XValueType > stride_iterator
Definition: MHO_NDArrayWrapper.hh:620
MHO_BidirectionalIterator< XValueType > iterator
Definition: MHO_NDArrayWrapper.hh:619
MHO_BidirectionalConstStrideIterator< XValueType > const_stride_iterator
Definition: MHO_NDArrayWrapper.hh:623
std::array< std::size_t, RANK > index_type
Definition: MHO_NDArrayWrapper.hh:45
#define min(a, b)
Definition: max555.c:9
Definition: MHO_AdhocFlagging.hh:18