array_mem_check.hpp
Go to the documentation of this file.
1 
8 /*****************************************************************************
9 ** Ifdefs
10 *****************************************************************************/
11 
12 #ifndef ECL_CONTAINERS_ARRAY_MEM_CHECK_HPP_
13 #define ECL_CONTAINERS_ARRAY_MEM_CHECK_HPP_
14 #ifdef ECL_MEM_CHECK_ARRAYS
15 
16 /*****************************************************************************
17 ** Includes
18 *****************************************************************************/
19 
20 #include <algorithm> // std::copy
21 #include <cstddef> // size_t
22 #include <iterator>
23 #include "../definitions.hpp"
24 #include "../initialiser.hpp"
25 #include "../stencil.hpp"
26 #include <ecl/config/macros.hpp>
27 #include <ecl/concepts/macros.hpp>
29 #include <ecl/concepts/streams.hpp>
32 
33 /*****************************************************************************
34 ** Namespaces
35 *****************************************************************************/
36 
37 namespace ecl {
38 
39 /*****************************************************************************
40 ** Forward Declarations
41 *****************************************************************************/
42 
43 namespace blueprints {
44 
45 template <typename Type, size_t N> class ArrayFactory;
46 template <typename Derived> class ArrayBluePrint;
47 template <typename Type, size_t Size> class ConstantArray;
48 
49 } // namespace blueprints
50 
51 namespace formatters {
52 
53 template <typename Type, size_t N> class ArrayFormatter;
54 
55 } // namespace formatters
56 
57 /*****************************************************************************
58 ** Interface [Array][Fixed]
59 *****************************************************************************/
105 template<typename Type, std::size_t Size = DynamicStorage>
106 class ECL_PUBLIC Array : public blueprints::ArrayFactory<Type,Size> {
107  public:
108  /*********************
109  ** Typedefs
110  **********************/
111  typedef Type value_type;
112  typedef Type* iterator;
113  typedef const Type* const_iterator;
114  typedef Type& reference;
115  typedef const Type& const_reference;
116  typedef std::size_t size_type;
117  typedef std::ptrdiff_t difference_type;
118  typedef std::reverse_iterator<iterator> reverse_iterator;
119  typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
120  typedef blueprints::ArrayFactory<value_type,Size> Factory;
121  typedef formatters::ArrayFormatter<Type,Size> Formatter;
123  /*********************
124  ** Constructors
125  **********************/
130  Array() { initialiseMagicSections(); };
153  template<typename T>
154  Array(const blueprints::ArrayBluePrint< T > &blueprint) {
155  ecl_compile_time_concept_check(BluePrintConcept<T>);
156  blueprint.implementApply(*this);
157  initialiseMagicSections();
158  }
159 
160  virtual ~Array() {}; // The user should manually check these in the classes that hold them.
161 
162  /*********************
163  ** Assignment
164  **********************/
178  containers::BoundedListInitialiser<Type,Type*,Size> operator<<(const Type &value) {
179  return containers::BoundedListInitialiser<value_type,iterator,Size>(value,elements);
180  }
181 
182  /*********************
183  ** Iterators
184  **********************/
189  iterator begin() { return elements; }
194  const_iterator begin() const { return elements; }
199  iterator end() { return elements+Size; }
204  const_iterator end() const { return elements+Size; }
209  reverse_iterator rbegin() { return reverse_iterator(end()); }
214  const_reverse_iterator rbegin() const { return const_reverse_iterator(end()); }
219  reverse_iterator rend() { return reverse_iterator(begin()); }
224  const_reverse_iterator rend() const { return const_reverse_iterator(begin()); }
225 
226  /*********************
227  ** Front/Back
228  **********************/
233  reference front() { return elements[0]; }
238  const_reference front() const { return elements[0]; }
243  reference back() { return elements[Size-1]; }
248  const_reference back() const { return elements[Size-1]; }
249 
250  /*********************
251  ** Accessors
252  **********************/
264  Stencil< Array<Type,Size> > stencil(const unsigned int& start_index, const unsigned int& n) {
265  ecl_assert_throw(start_index < Size, StandardException(LOC, OutOfRangeError, "Start index provided is larger than the underlying array size."));
266  ecl_assert_throw(start_index+n <= Size, StandardException(LOC, OutOfRangeError, "Finish index provided is larger than the underlying array size."));
267  return Stencil< Array<Type,Size> >(*this, begin()+start_index, begin()+start_index+n);
268  }
278  reference operator[](size_type i) {
279  ecl_assert_throw( i<Size, StandardException(LOC,OutOfRangeError));
280  return elements[i];
281  }
293  const_reference operator[](size_type i) const {
294  ecl_assert_throw( i<Size, StandardException(LOC,OutOfRangeError));
295  return elements[i];
296  }
307  reference at(size_type i) throw(StandardException) {
308  if ( i>=Size ) {
309  throw StandardException(LOC,OutOfRangeError);
310  }
311  return elements[i];
312  }
325  const_reference at(size_type i) const throw(StandardException) {
326  if ( i>=Size ) {
327  throw StandardException(LOC,OutOfRangeError);
328  }
329  return elements[i];
330  }
331 
332  /*********************
333  ** Utilities
334  **********************/
340  static size_type size() { return Size; }
341 
342  /*********************
343  ** Streaming
344  **********************/
352  template <typename OutputStream, typename ElementType, size_t ArraySize>
353  friend OutputStream& operator<<(OutputStream &ostream , const Array<ElementType,ArraySize> &array);
354 
355  /******************************************
356  ** Buffer under/overrun checks
357  *******************************************/
358  bool bufferUnderRun();
359  bool bufferOverRun();
360  bool bufferOverFlow();
361 
362  private:
363  void initialiseMagicSections();
364 
365  static const unsigned int& bufferOverrunLength() {
366  static const unsigned int buffer_overrun_length = 4;
367  return buffer_overrun_length;
368  }
369  static const unsigned int& bufferUnderrunLength() {
370  static const unsigned int buffer_underrun_length = 4;
371  return buffer_underrun_length;
372  }
373  static const char& magicChar() {
374  static const char magic_char = 0xCC;
375  return magic_char;
376  }
377  char underrun[4];
378  value_type elements[Size];
379  char overrun[4];
380 };
381 
382 /*****************************************************************************
383 ** Implementation [Array]
384 *****************************************************************************/
391 template<typename Type, size_t Size>
392 void Array<Type,Size>::initialiseMagicSections() {
393 
394  for ( unsigned int i = 0; i < bufferUnderrunLength(); ++i ) {
395  underrun[i] = magicChar();
396  }
397  for ( unsigned int i = 0; i < bufferOverrunLength(); ++i ) {
398  overrun[i] = magicChar();
399  }
400 
401 }
411 template<typename Type, size_t Size>
412 bool Array<Type,Size>::bufferOverRun() {
413 
414  for ( unsigned int i = 0; i < bufferOverrunLength(); ++i ) {
415  if ( overrun[i] != magicChar() ) {
416  return true;
417  }
418  }
419  return false;
420 }
421 
430 template<typename Type, size_t Size>
431 bool Array<Type,Size>::bufferUnderRun() {
432  for ( unsigned int i = 0; i < bufferUnderrunLength(); ++i ) {
433  if ( underrun[i] != magicChar() ) {
434  return true;
435  }
436  }
437  return false;
438 }
448 template<typename Type, size_t Size>
449 bool Array<Type,Size>::bufferOverFlow() {
450  return ( bufferOverRun() || bufferUnderRun() );
451 }
452 
453 
454 /*****************************************************************************
455 ** Implementation [Array][Streaming]
456 *****************************************************************************/
457 
458 template <typename OutputStream, typename ElementType, size_t ArraySize>
459 OutputStream& operator<<(OutputStream &ostream , const Array<ElementType,ArraySize> &array) {
460 
461  ecl_compile_time_concept_check(StreamConcept<OutputStream>);
462 
463  ostream << "[ ";
464  for(size_t i = 0; i < ArraySize; ++i )
465  {
466  ostream << array[i] << " ";
467  }
468  ostream << "]";
469  ostream.flush();
470 
471  return ostream;
472 }
473 
474 /*****************************************************************************
475 ** BluePrints
476 *****************************************************************************/
477 
478 namespace blueprints {
479 
504 template <typename Derived>
505 class ArrayBluePrint {
506  public:
519  template <typename BaseType>
520  BaseType implementInstantiate() {
521  return static_cast<Derived*>(this)->instantiate();
522  }
536  template <typename BaseType>
537  void implementApply(BaseType& array) const {
538  static_cast<const Derived*>(this)->apply(array);
539  }
540 
541  virtual ~ArrayBluePrint() {}
542 };
551 template <typename Type, size_t Size>
552 class ConstantArray : public ArrayBluePrint< ConstantArray<Type, Size> > {
553  public:
557  typedef ecl::Array<Type,Size> base_type;
566  ConstantArray(const Type& value = 0) : val(value) {}
567 
568  virtual ~ConstantArray() {};
569 
580  base_type instantiate() {
581  ecl::Array<Type,Size> array;
582  std::fill_n(array.begin(),Size,val);
583  return array;
584  }
585 
590  void apply(base_type& array) const {
591  std::fill_n(array.begin(),Size,val);
592  }
593 
594  private:
595  const Type& val;
596 };
597 
606 template<typename Type, size_t Size>
607 class ArrayFactory {
608  public:
615  static ConstantArray<Type,Size> Constant(const Type& value) {
616  return ConstantArray<Type,Size>(value);
617  }
618 
619  virtual ~ArrayFactory() {};
620 };
621 
622 } // namespace blueprints
623 } // namespace ecl
624 
625 #endif /* ECL_MEM_CHECK_ARRAYS */
626 #endif /* ECL_CONTAINERS_ARRAY_MEM_CHECK_HPP_ */
Fixed size container with a few bells and whistles.
Embedded control libraries.
OutputStream & operator<<(OutputStream &ostream, Format< std::string > &formatter)
#define ecl_assert_throw(expression, exception)
OutOfRangeError
#define ecl_compile_time_concept_check(Model)
#define ECL_PUBLIC


ecl_containers
Author(s): Daniel Stonier
autogenerated on Mon Feb 28 2022 22:18:43