Rosetta
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
Chunk.hh
Go to the documentation of this file.
1 #ifndef INCLUDED_ObjexxFCL_Chunk_hh
2 #define INCLUDED_ObjexxFCL_Chunk_hh
3 
4 
5 // Chunk: Contiguous Array for Use in ChunkVector
6 //
7 // Project: Objexx Fortran Compatibility Library (ObjexxFCL)
8 //
9 // Version: 3.0.0
10 //
11 // Language: C++
12 //
13 // Copyright (c) 2000-2009 Objexx Engineering, Inc. All Rights Reserved.
14 // Use of this source code or any derivative of it is restricted by license.
15 // Licensing is available from Objexx Engineering, Inc.: http://objexx.com Objexx@objexx.com
16 
17 
18 // C++ Headers
19 #include <algorithm>
20 #include <cassert>
21 #include <cstddef>
22 #include <limits>
23 
24 
25 namespace ObjexxFCL {
26 
27 
28 /// @brief Chunk: Contiguous Array for Use in ChunkVector
29 ///
30 /// @remarks
31 /// @li size <= capacity
32 /// @li capacity == size after construction
33 /// @li capacity == size after assignment if reallocation required
34 template< typename T >
35 class Chunk
36 {
37 
38 
39 private: // Friend
40 
41 
42  template< typename > friend class Chunk;
43 
44 
45 public: // Types
46 
47 
48  // STL style
49  typedef T value_type;
50  typedef T & reference;
51  typedef T const & const_reference;
52  typedef T * pointer;
53  typedef T const * const_pointer;
54  typedef std::size_t size_type;
55 
56  // C++ style
57  typedef T Value;
58  typedef T & Reference;
59  typedef T const & ConstReference;
60  typedef T * Pointer;
61  typedef T const * ConstPointer;
62  typedef std::size_t Size;
63 
64 
65 public: // Creation
66 
67 
68  /// @brief Default Constructor
69  inline
70  Chunk() :
71  size_( 0 ),
72  capacity_( 0 ),
73  array_( 0 )
74  {}
75 
76 
77  /// @brief Copy Constructor
78  inline
79  Chunk( Chunk const & c ) :
80  size_( c.size_ ),
81  capacity_( size_ ),
82  array_( size_ > 0 ? new T[ size_ ] : 0 )
83  {
84  for ( size_type i = 0; i < size_; ++i ) {
85  array_[ i ] = c.array_[ i ];
86  }
87  }
88 
89 
90  /// @brief Copy Constructor Template
91  template< typename U >
92  inline
93  explicit
94  Chunk( Chunk< U > const & c ) :
95  size_( c.size_ ),
96  capacity_( size_ ),
97  array_( size_ > 0 ? new T[ size_ ] : 0 )
98  {
99  for ( size_type i = 0; i < size_; ++i ) {
100  array_[ i ] = T( c.array_[ i ] );
101  }
102  }
103 
104 
105  /// @brief Size Constructor: Built-In Types are Not Initialized!
106  inline
107  explicit
108  Chunk( size_type const size_a ) :
109  size_( size_a ),
110  capacity_( size_ ),
111  array_( size_ > 0 ? new T[ size_ ] : 0 )
112  {}
113 
114 
115  /// @brief Size + Uniform Value Constructor
116  inline
118  size_type const size_a,
119  T const & value
120  ) :
121  size_( size_a ),
122  capacity_( size_ ),
123  array_( size_ > 0 ? new T[ size_ ] : 0 )
124  {
125  for ( size_type i = 0; i < size_; ++i ) {
126  array_[ i ] = value;
127  }
128  }
129 
130 
131  /// @brief Destructor
132  inline
134  {
135  delete[] array_;
136  }
137 
138 
139 public: // Assignment
140 
141 
142  /// @brief Copy Assignment
143  inline
144  Chunk &
145  operator =( Chunk const & c )
146  {
147  if ( this != &c ) {
148  if ( size_ != c.size_ ) {
149  size_ = c.size_;
150  capacity_ = size_;
151  delete[] array_; array_ = ( size_ > 0 ? new T[ size_ ] : 0 );
152  }
153  for ( size_type i = 0; i < size_; ++i ) {
154  array_[ i ] = c.array_[ i ];
155  }
156  }
157  return *this;
158  }
159 
160 
161  /// @brief Copy Assignment Template
162  template< typename U >
163  inline
164  Chunk &
165  operator =( Chunk< U > const & c )
166  {
167  if ( size_ != c.size_ ) {
168  size_ = c.size_;
169  capacity_ = size_;
170  delete[] array_; array_ = ( size_ > 0 ? new T[ size_ ] : 0 );
171  }
172  for ( size_type i = 0; i < size_; ++i ) {
173  array_[ i ] = T( c.array_[ i ] );
174  }
175  return *this;
176  }
177 
178 
179  /// @brief Size + Value Assignment
180  inline
181  Chunk &
183  size_type const size_a,
184  T const & value
185  )
186  {
187  if ( size_ != size_a ) {
188  size_ = size_a;
189  capacity_ = size_;
190  delete[] array_; array_ = ( size_ > 0 ? new T[ size_ ] : 0 );
191  }
192  for ( size_type i = 0; i < size_; ++i ) {
193  array_[ i ] = value;
194  }
195  return *this;
196  }
197 
198 
199  /// @brief += Chunk
200  inline
201  Chunk &
202  operator +=( Chunk const & c )
203  {
204  assert( size_ == c.size_ );
205  for ( size_type i = 0; i < size_; ++i ) {
206  array_[ i ] += c.array_[ i ];
207  }
208  return *this;
209  }
210 
211 
212  /// @brief -= Chunk
213  inline
214  Chunk &
215  operator -=( Chunk const & c )
216  {
217  assert( size_ == c.size_ );
218  for ( size_type i = 0; i < size_; ++i ) {
219  array_[ i ] -= c.array_[ i ];
220  }
221  return *this;
222  }
223 
224 
225  /// @brief += Chunk Template
226  template< typename U >
227  inline
228  Chunk &
229  operator +=( Chunk< U > const & c )
230  {
231  assert( size_ == c.size_ );
232  for ( size_type i = 0; i < size_; ++i ) {
233  array_[ i ] += T( c.array_[ i ] );
234  }
235  return *this;
236  }
237 
238 
239  /// @brief -= Chunk Template
240  template< typename U >
241  inline
242  Chunk &
243  operator -=( Chunk< U > const & c )
244  {
245  assert( size_ == c.size_ );
246  for ( size_type i = 0; i < size_; ++i ) {
247  array_[ i ] -= T( c.array_[ i ] );
248  }
249  return *this;
250  }
251 
252 
253  /// @brief = Value
254  inline
255  Chunk &
256  operator =( T const & value )
257  {
258  for ( size_type i = 0; i < size_; ++i ) {
259  array_[ i ] = value;
260  }
261  return *this;
262  }
263 
264 
265  /// @brief += Value
266  inline
267  Chunk &
268  operator +=( T const & value )
269  {
270  for ( size_type i = 0; i < size_; ++i ) {
271  array_[ i ] += value;
272  }
273  return *this;
274  }
275 
276 
277  /// @brief -= Value
278  inline
279  Chunk &
280  operator -=( T const & value )
281  {
282  for ( size_type i = 0; i < size_; ++i ) {
283  array_[ i ] -= value;
284  }
285  return *this;
286  }
287 
288 
289  /// @brief *= Value
290  inline
291  Chunk &
292  operator *=( T const & value )
293  {
294  for ( size_type i = 0; i < size_; ++i ) {
295  array_[ i ] *= value;
296  }
297  return *this;
298  }
299 
300 
301  /// @brief /= Value
302  inline
303  Chunk &
304  operator /=( T const & value )
305  {
306  assert( value != T( 0 ) );
307  for ( size_type i = 0; i < size_; ++i ) {
308  array_[ i ] /= value;
309  }
310  return *this;
311  }
312 
313 
314 public: // Subscript
315 
316 
317  /// @brief Chunk[ i ] const: 0-Based Indexing
318  inline
319  T const &
320  operator []( size_type const i ) const
321  {
322  assert( i < size_ );
323  return array_[ i ];
324  }
325 
326 
327  /// @brief Chunk[ i ]: 0-Based Indexing
328  inline
329  T &
331  {
332  assert( i < size_ );
333  return array_[ i ];
334  }
335 
336 
337 public: // Inspector
338 
339 
340  /// @brief Size
341  inline
342  size_type
343  size() const
344  {
345  return size_;
346  }
347 
348 
349  /// @brief Capacity
350  inline
351  size_type
352  capacity() const
353  {
354  return capacity_;
355  }
356 
357 
358  /// @brief Maximum Size
359  inline
360  size_type
361  max_size() const
362  {
364  }
365 
366 
367  /// @brief Empty?
368  inline
369  bool
370  empty() const
371  {
372  return ( size_ == 0 );
373  }
374 
375 
376  /// @brief First Element
377  inline
378  T const &
379  front() const
380  {
381  assert( size_ > 0 );
382  return array_[ 0 ];
383  }
384 
385 
386  /// @brief Last Element
387  inline
388  T const &
389  back() const
390  {
391  assert( size_ > 0 );
392  return array_[ size_ - 1 ];
393  }
394 
395 
396 public: // Modifier
397 
398 
399  /// @brief First Element
400  inline
401  T &
403  {
404  assert( size_ > 0 );
405  return array_[ 0 ];
406  }
407 
408 
409  /// @brief Last Element
410  inline
411  T &
413  {
414  assert( size_ > 0 );
415  return array_[ size_ - 1 ];
416  }
417 
418 
419  /// @brief Append an Element
420  inline
421  Chunk &
422  push_back( T const & value )
423  {
424  assert( size_ < max_size() );
425  if ( size_ == capacity_ ) reserve( 2 * capacity_ );
426  array_[ size_ ] = value;
427  ++size_;
428  return *this;
429  }
430 
431 
432  /// @brief Remove the Last Element
433  inline
434  Chunk &
436  {
437  assert( size_ > 0 );
438  --size_;
439  return *this;
440  }
441 
442 
443  /// @brief Resize: Values Preserved: Added Built-In Values are Not Initialized!
444  inline
445  Chunk &
446  resize( size_type const size_a )
447  {
448  if ( size_ != size_a ) {
449  if ( size_a > capacity_ ) {
450  size_type const size_c( std::min( size_, size_a ) );
451  T * const new_array( new T[ size_a ] );
452  for ( size_type i = 0; i < size_c; ++i ) {
453  new_array[ i ] = array_[ i ];
454  }
455  delete[] array_; array_ = new_array;
456  capacity_ = size_a;
457  }
458  size_ = size_a;
459  }
460  return *this;
461  }
462 
463 
464  /// @brief Resize + Fill Value: Values Preserved
465  inline
466  Chunk &
468  size_type const size_a,
469  T const & value
470  )
471  {
472  if ( size_ != size_a ) {
473  size_type const size_c( std::min( size_, size_a ) );
474  if ( size_a > capacity_ ) {
475  T * const new_array( new T[ size_a ] );
476  for ( size_type i = 0; i < size_c; ++i ) {
477  new_array[ i ] = array_[ i ];
478  }
479  delete[] array_; array_ = new_array;
480  capacity_ = size_a;
481  }
482  for ( size_type i = size_c; i < size_a; ++i ) {
483  array_[ i ] = value;
484  }
485  size_ = size_a;
486  }
487  return *this;
488  }
489 
490 
491  /// @brief Resize: Values Not Preserved: Built-In Values are Not Initialized!
492  inline
493  Chunk &
495  {
496  if ( size_ != size_a ) {
497  if ( size_a > capacity_ ) {
498  delete[] array_; array_ = new T[ size_a ];
499  capacity_ = size_a;
500  }
501  size_ = size_a;
502  }
503  return *this;
504  }
505 
506 
507  /// @brief Resize + Fill Value: Values Not Preserved
508  inline
509  Chunk &
511  size_type const size_a,
512  T const & value
513  )
514  {
515  if ( size_ != size_a ) {
516  if ( size_a > capacity_ ) {
517  delete[] array_; array_ = new T[ size_a ];
518  capacity_ = size_a;
519  }
520  size_ = size_a;
521  }
522  for ( size_type i = 0; i < size_; ++i ) {
523  array_[ i ] = value;
524  }
525  return *this;
526  }
527 
528 
529  /// @brief Reserve: Values Preserved: Added Built-In Values are Not Initialized!
530  inline
531  Chunk &
532  reserve( size_type const capacity_a )
533  {
534  if ( capacity_ < capacity_a ) {
535  T * const new_array( new T[ capacity_a ] );
536  for ( size_type i = 0; i < size_; ++i ) {
537  new_array[ i ] = array_[ i ];
538  }
539  delete[] array_; array_ = new_array;
540  capacity_ = capacity_a;
541  }
542  return *this;
543  }
544 
545 
546  /// @brief Shrink Capacity to Size
547  inline
548  Chunk &
550  {
551  if ( size_ < capacity_ ) {
552  T * const new_array( ( size_ > 0 ? new T[ size_ ] : 0 ) );
553  for ( size_type i = 0; i < size_; ++i ) {
554  new_array[ i ] = array_[ i ];
555  }
556  delete[] array_; array_ = new_array;
557  capacity_ = size_;
558  }
559  return *this;
560  }
561 
562 
563  /// @brief Swap
564  inline
565  void
566  swap( Chunk & c )
567  {
568  std::swap( size_, c.size_ );
570  std::swap( array_, c.array_ );
571  }
572 
573 
574  /// @brief Clear
575  inline
576  Chunk &
578  {
579  size_ = 0;
580  capacity_ = 0;
581  delete[] array_; array_ = 0;
582  return *this;
583  }
584 
585 
586 public: // Comparison
587 
588 
589  /// @brief Chunk == Chunk
590  friend
591  inline
592  bool
593  operator ==( Chunk const & a, Chunk const & b )
594  {
595  if ( &a == &b ) { // Same objects
596  return true;
597  } else if ( a.size_ != b.size_ ) { // Sizes differ
598  return false;
599  } else { // Compare values
600  for ( size_type i = 0, ie = a.size_; i < ie; ++i ) {
601  if ( a.array_[ i ] != b.array_[ i ] ) return false; // Elements differ
602  }
603  return true; // No elements differ
604  }
605  }
606 
607 
608  /// @brief Chunk != Chunk
609  friend
610  inline
611  bool
612  operator !=( Chunk const & a, Chunk const & b )
613  {
614  return !( a == b );
615  }
616 
617 
618 public: // Friend
619 
620 
621  /// @brief Swap
622  friend
623  inline
624  void
625  swap( Chunk & a, Chunk & b )
626  {
627  a.swap( b );
628  }
629 
630 
631 private: // Data
632 
633 
634  /// @brief Number of elements in use
636 
637  /// @brief Number of elements it can hold without resizing
639 
640  /// @brief Data array
642 
643 
644 }; // Chunk
645 
646 
647 /// @brief Chunk == Chunk
648 template< typename T >
649 bool
650 operator ==( Chunk< T > const & a, Chunk< T > const & b );
651 
652 
653 /// @brief Chunk != Chunk
654 template< typename T >
655 bool
656 operator !=( Chunk< T > const & a, Chunk< T > const & b );
657 
658 
659 /// @brief Swap
660 template< typename T >
661 void
662 swap( Chunk< T > & a, Chunk< T > & b );
663 
664 
665 } // namespace ObjexxFCL
666 
667 
668 #ifndef NO_STD_SWAP_OVERLOADS
669 
670 
671 // std::swap Overloads for Efficiency
672 //
673 // Technically you cannot add template functions overloads to namespace std
674 // but this works with most compilers and makes it much faster if someone uses
675 // std::swap instead of swap or ObjexxFCL::swap. The legal alternative would be
676 // to add specializations of swap for each anticipated instantiation.
677 
678 
679 namespace std {
680 
681 
682 /// @brief std::swap( Chunk, Chunk )
683 template< typename T >
684 inline
685 void
687 {
688  a.swap( b );
689 }
690 
691 
692 } // namespace std
693 
694 
695 #endif // NO_STD_SWAP_OVERLOADS
696 
697 
698 #endif // INCLUDED_ObjexxFCL_Chunk_HH
T const * ConstPointer
Definition: Chunk.hh:61
size_type size_
Number of elements in use.
Definition: Chunk.hh:635
Chunk & assign(size_type const size_a, T const &value)
Size + Value Assignment.
Definition: Chunk.hh:182
static T min(T x, T y)
Definition: Svm.cc:16
bool operator!=(byte const &i, byte const &j)
byte != byte
Definition: byte.hh:356
T const & front() const
First Element.
Definition: Chunk.hh:379
Chunk(Chunk const &c)
Copy Constructor.
Definition: Chunk.hh:79
Chunk & operator=(Chunk const &c)
Copy Assignment.
Definition: Chunk.hh:145
Chunk & operator-=(Chunk const &c)
-= Chunk
Definition: Chunk.hh:215
Chunk & pop_back()
Remove the Last Element.
Definition: Chunk.hh:435
Chunk & operator*=(T const &value)
*= Value
Definition: Chunk.hh:292
Chunk & clear()
Clear.
Definition: Chunk.hh:577
static void swap(T &x, T &y)
Definition: Svm.cc:21
std::size_t Size
Definition: Chunk.hh:62
void swap(Chunk &c)
Swap.
Definition: Chunk.hh:566
Chunk & operator+=(Chunk const &c)
+= Chunk
Definition: Chunk.hh:202
Chunk()
Default Constructor.
Definition: Chunk.hh:70
T const & const_reference
Definition: Chunk.hh:51
size_type capacity_
Number of elements it can hold without resizing.
Definition: Chunk.hh:638
Chunk & reserve(size_type const capacity_a)
Reserve: Values Preserved: Added Built-In Values are Not Initialized!
Definition: Chunk.hh:532
std::size_t size_type
Definition: Chunk.hh:54
Chunk(size_type const size_a, T const &value)
Size + Uniform Value Constructor.
Definition: Chunk.hh:117
member1 value
Definition: Tag.cc:296
T * array_
Data array.
Definition: Chunk.hh:641
size_type capacity() const
Capacity.
Definition: Chunk.hh:352
Chunk & resize(size_type const size_a, T const &value)
Resize + Fill Value: Values Preserved.
Definition: Chunk.hh:467
Chunk & non_preserving_resize(size_type const size_a, T const &value)
Resize + Fill Value: Values Not Preserved.
Definition: Chunk.hh:510
T const * const_pointer
Definition: Chunk.hh:53
size_type size() const
Size.
Definition: Chunk.hh:343
Chunk(Chunk< U > const &c)
Copy Constructor Template.
Definition: Chunk.hh:94
Chunk & push_back(T const &value)
Append an Element.
Definition: Chunk.hh:422
Chunk & non_preserving_resize(size_type const size_a)
Resize: Values Not Preserved: Built-In Values are Not Initialized!
Definition: Chunk.hh:494
T & back()
Last Element.
Definition: Chunk.hh:412
size_type max_size() const
Maximum Size.
Definition: Chunk.hh:361
T const & back() const
Last Element.
Definition: Chunk.hh:389
Chunk & operator/=(T const &value)
/= Value
Definition: Chunk.hh:304
bool empty() const
Empty?
Definition: Chunk.hh:370
T const & operator[](size_type const i) const
Chunk[ i ] const: 0-Based Indexing.
Definition: Chunk.hh:320
friend bool operator==(Chunk const &a, Chunk const &b)
Chunk == Chunk.
Definition: Chunk.hh:593
T & front()
First Element.
Definition: Chunk.hh:402
Chunk & shrink()
Shrink Capacity to Size.
Definition: Chunk.hh:549
Chunk(size_type const size_a)
Size Constructor: Built-In Types are Not Initialized!
Definition: Chunk.hh:108
friend bool operator!=(Chunk const &a, Chunk const &b)
Chunk != Chunk.
Definition: Chunk.hh:612
void swap(CArray< T > &a, CArray< T > &b)
Swap.
Definition: CArray.hh:1403
Chunk: Contiguous Array for Use in ChunkVector.
Definition: Chunk.hh:35
T const & ConstReference
Definition: Chunk.hh:59
static T max(T x, T y)
Definition: Svm.cc:19
bool operator==(byte const &i, byte const &j)
byte == byte
Definition: byte.hh:346
Chunk & resize(size_type const size_a)
Resize: Values Preserved: Added Built-In Values are Not Initialized!
Definition: Chunk.hh:446
~Chunk()
Destructor.
Definition: Chunk.hh:133