CoreDX Data Distribution Service
The High Performance, Small Footprint DDS from Twin Oaks Computing, Inc
dds_seq.hh
Go to the documentation of this file.
1 /*****************************************************************
2  *
3  * file: dds_seq.hh
4  * desc: CoreDX DDS API for sequences
5  *
6  *****************************************************************
7  *
8  * Copyright(C) 2006-2020 Twin Oaks Computing, Inc
9  * All rights reserved. Castle Rock, CO 80108
10  *
11  *****************************************************************
12  *
13  * This software has been provided pursuant to a License Agreement
14  * containing restrictions on its use. This software contains
15  * valuable trade secrets and proprietary information of
16  * Twin Oaks Computing, Inc and is protected by law. It may not be
17  * copied or distributed in any form or medium, disclosed to third
18  * parties, reverse engineered or used in any manner not provided
19  * for in said License Agreement except with the prior written
20  * authorization from Twin Oaks Computing, Inc.
21  *
22  *****************************************************************/
23 
24 #ifndef _DDS_SEQ_HH
25 #define _DDS_SEQ_HH
26 
27 # include <dds/toc_util.h>
28 # if defined(COREDX_DDS_SEQ_EX)
29 # include <stdexcept>
30 # endif
31 
46 namespace DDS
47 {
48 
49  template <class T,uint32_t bound> class bounded_seq;
50 
61  template <class T> class sequence {
62  public:
64  sequence();
68  sequence(const sequence &x);
72  ~sequence();
77  this->resize(x.core_seq._length);
78  for (unsigned int i = 0; i < this->core_seq._length; i++)
79  this->core_seq._buffer[i] = x.core_seq._buffer[i]; // will do deep copy if implemented on T
80  return *this;
81  };
82 
83  // capacity
85  uint32_t size() const;
87  uint32_t length() const;
91  uint32_t capacity() const; // get current capactity
104  bool reserve(uint32_t n); // set capacity
105  void size(uint32_t n); // set size within limits of capacity
114  bool resize(uint32_t n); // set capacity and size
117  void maximum(uint32_t n); // set maximum
120  uint32_t maximum() const; // get current maximum
121 
123  bool empty() const; // test if empty
125  void shrink_to_fit(); // reduce capacity to fit size
126 
130  void assign(T* buffer, uint32_t n); // provide array of elements of size 'n', takes ownership of the memory
131 
135  T* release(); // release sequence contents to caller (if successful, sequence is empty after this)
136 
137  // element access
139  T& operator[] (uint32_t n);
141  const T& operator[] (uint32_t n) const;
143  T& at (uint32_t n);
145  const T& at (uint32_t n) const;
147  T& front ();
149  const T& front () const;
151  T& back ();
153  const T& back () const;
154 
156  const T* buffer() const;
157 
158  // modifiers
164  bool push_back(const T& v);
166  void pop_back();
168  void swap(sequence& x);
170  void clear();
171 
172  private:
173 
174  typedef struct CoreSeqType
175  {
176  T * _buffer;
177  unsigned int _maximum;
178  unsigned int _length;
179  unsigned int _size;
180  unsigned char _own;
181  unsigned int _item_size;
182  } CoreSeqType_t;
183 
184  CoreSeqType_t core_seq;
185 
186  template <class TY,uint32_t BOUND> friend class bounded_sequence;
187 
188  };
189 
190 
191  template<class T>
193  INIT_SEQ(this->core_seq);
194  this->core_seq._item_size = sizeof(T);
195  }
196 
197  // copy constructor
198  template<class T>
200  INIT_SEQ(this->core_seq);
201  this->core_seq._item_size = sizeof(T);
202  (*this) = x;
203  }
204 
205  template<class T>
207  clear();
208  }
209 
210  // capacity
211  template<class T>
212  uint32_t
214  return this->core_seq._size;
215  }
216 
217  template<class T>
218  uint32_t sequence<T>::size() const {
219  return this->core_seq._length;
220  }
221 
222  template<class T>
223  uint32_t sequence<T>::length() const {
224  return this->core_seq._length;
225  }
226 
227  template<class T>
228  void sequence<T>::maximum(uint32_t n)
229  {
230  this->core_seq._maximum = n;
231  }
232 
233  template<class T>
234  uint32_t sequence<T>::maximum() const {
235  return this->core_seq._maximum;
236  }
237 
238  template<class T>
239  bool
241  return (this->core_seq._length == 0)?true:false;
242  }
243 
244  // reserve(n)
245  // allocate memory to hold up to 's' items (capacity)
246  // will truncate if 'n' is smaller than current capacity
247  // will honor maximum 'bound'
248  template<class T>
249  bool
250  sequence<T>::reserve(uint32_t n) {
251  bool retval = true;
252  T * tmpbuf = static_cast<T*>(0);
253  if (n > 0)
254  {
255  if ( ( this->core_seq._maximum == 0 ) ||
256  ( this->core_seq._maximum >= n ) )
257  {
258  T * newbuf = new T[n];
259  if (newbuf)
260  {
261  this->core_seq._size = n;
262  if (this->core_seq._length > n)
263  this->core_seq._length = n; // truncated
264 
265  if (this->core_seq._buffer)
266  for (uint32_t i = 0;i < this->core_seq._length; i++)
267  newbuf[i] = this->core_seq._buffer[i];
268  tmpbuf = this->core_seq._buffer;
269  this->core_seq._buffer = newbuf;
270  }
271  else
272  retval = false; // failed to alloc
273  }
274  else
275  retval = false; // would exceed bound
276  }
277  else
278  {
279  this->core_seq._size = 0;
280  this->core_seq._length = 0;
281  tmpbuf = this->core_seq._buffer;
282  this->core_seq._buffer = 0;
283  }
284  if ( tmpbuf )
285  delete[] tmpbuf;
286  return retval;
287  }
288 
289  template<class T>
290  bool sequence<T>::resize(uint32_t n) {
291  bool retval;
292  retval = reserve(n);
293  if (this->core_seq._size == n)
294  this->core_seq._length = n;
295  return retval;
296  }
297 
298  template<class T>
299  void sequence<T>::size(uint32_t n) {
300  if (this->core_seq._size >= n)
301  this->core_seq._length = n;
302  }
303 
304  template<class T>
305  void
307  resize(this->core_seq._length);
308  }
309 
310  // element access
311  template<class T>
312  T&
314 #if defined(COREDX_DDS_SEQ_EX)
315  if ( n >= this->core_seq._size )
316  throw std::out_of_range("n");
317 #endif
318  return this->core_seq._buffer[n];
319  }
320 
321  template<class T>
322  const T&
323  sequence<T>::operator[] (uint32_t n) const {
324 #if defined(COREDX_DDS_SEQ_EX)
325  if ( n >= this->core_seq._size )
326  throw std::out_of_range("n");
327 #endif
328  return this->core_seq._buffer[n];
329  }
330 
331  template<class T> T& sequence<T>::at (uint32_t n) {
332 #if defined(COREDX_DDS_SEQ_EX)
333  if ( n >= this->core_seq._size )
334  throw std::out_of_range("n");
335 #endif
336  return (*this)[n];
337  }
338  template<class T> const T& sequence<T>::at (uint32_t n) const {
339 #if defined(COREDX_DDS_SEQ_EX)
340  if ( n >= this->core_seq._size )
341  throw std::out_of_range("n");
342 #endif
343  return (*this)[n];
344  }
345  template<class T> T& sequence<T>::front () {
346 #if defined(COREDX_DDS_SEQ_EX)
347  if ( this->core_seq._size == 0 )
348  throw std::out_of_range("index");
349 #endif
350  return (*this)[0];
351  }
352  template<class T> const T& sequence<T>::front () const {
353 #if defined(COREDX_DDS_SEQ_EX)
354  if ( this->core_seq._size == 0 )
355  throw std::out_of_range("index");
356 #endif
357  return (*this)[0];
358  }
359 
360  template<class T> T& sequence<T>::back () {
361 #if defined(COREDX_DDS_SEQ_EX)
362  if ( this->core_seq._length == 0 )
363  throw std::out_of_range("index");
364 #endif
365  return (*this)[this->core_seq._length-1];
366  }
367  template<class T> const T& sequence<T>::back () const {
368 #if defined(COREDX_DDS_SEQ_EX)
369  if ( this->core_seq._length == 0 )
370  throw std::out_of_range("index");
371 #endif
372  return (*this)[this->core_seq._length-1];
373  }
374  template<class T> const T* sequence<T>::buffer () const {
375  return this->core_seq._buffer;
376  }
377 
378  // modifiers
379  template<class T> bool sequence<T>::push_back(const T& v) {
380  bool retval;
381 
382  if (this->capacity() <= this->size())
383  reserve(this->size() + 2);
384 
385  if (this->size() < this->capacity() )
386  {
387  this->core_seq._buffer[this->size()] = v;
388  this->core_seq._length ++;
389  retval = true;
390  }
391  else
392  retval = false;
393  return retval;
394  }
395 
396  template<class T> void sequence<T>::pop_back() {
397  if (this->core_seq._length > 0) this->core_seq._length--;
398  }
399 
400  template<class T> void sequence<T>::swap(sequence& x) {
401  CoreSeqType tmp;
402  tmp = this->core_seq;
403  this->core_seq = x.core_seq;
404  x.core_seq = tmp;
405  }
406 
407  template<class T> void sequence<T>::clear() {
408  delete[] this->core_seq._buffer;
409  this->core_seq._buffer = 0;
410  this->core_seq._length = 0;
411  this->core_seq._size = 0;
412  }
413 
414  template<class T>
415  void sequence<T>::assign(T* buf, uint32_t n) {
416  delete[] this->core_seq._buffer;
417  this->core_seq._buffer = buf;
418  this->core_seq._length = n;
419  this->core_seq._size = n;
420  }
421 
422  template<class T>
424  T* retval = this->core_seq._buffer;
425  this->core_seq._buffer = NULL;
426  this->core_seq._length = 0;
427  this->core_seq._size = 0;
428  return retval;
429  }
430 
431 
432  template <class T,uint32_t BOUND> class bounded_sequence : public sequence<T> {
433  public:
434  bounded_sequence();
435  };
436 
437  template<class T,uint32_t BOUND>
438  bounded_sequence<T, BOUND>::bounded_sequence() : sequence<T>() {
439  this->core_seq._maximum = BOUND;
440  }
441 
442 
443 
444 # define CPP_DECLARE_UNBOUNDED_SEQ( type, name ) typedef DDS::sequence<type> name
445 # define DECLARE_CPP_UNBOUNDED_SEQ( type, name ) typedef DDS::sequence<type> name
446 
447 # define CPP_DECLARE_BOUNDED_SEQ( type, bound, name ) typedef DDS::bounded_sequence<type,bound> name
448 # define DECLARE_CPP_BOUNDED_SEQ( type, bound, name ) typedef DDS::bounded_sequence<type,bound> name
449 
450 } // namespace DDS
451 #endif
452 
453 
T & front()
Definition: dds_seq.hh:345
T * release()
Release current sequence contents, caller takes ownership of the memory. If successful, the sequence is empty after this operation.
Definition: dds_seq.hh:423
void assign(T *buffer, uint32_t n)
Caller provides an array of elements of size &#39;n&#39;. The Sequence takes ownership of the memory...
Definition: dds_seq.hh:415
uint32_t maximum() const
set the &#39;maximum&#39; length of the sequence
Definition: dds_seq.hh:234
uint32_t size() const
Returns the current size (number of elements) of the sequence.
Definition: dds_seq.hh:218
T & back()
Definition: dds_seq.hh:360
uint32_t length() const
alias for size()
Definition: dds_seq.hh:223
Sequence data type.
Definition: dds_seq.hh:61
void clear()
Definition: dds_seq.hh:407
T & operator[](uint32_t n)
Definition: dds_seq.hh:313
~sequence()
destroy the sequence and release resources. Destroys sequence contents.
Definition: dds_seq.hh:206
sequence & operator=(const sequence &x)
assignment operator Copies seqeuence contents.
Definition: dds_seq.hh:76
void pop_back()
Definition: dds_seq.hh:396
Provides the DDS infrastructure.
Definition: dds_builtin_basic.hh:27
void shrink_to_fit()
reduce &#39;capacity&#39; to match &#39;size&#39;
Definition: dds_seq.hh:306
bool resize(uint32_t n)
Set the &#39;capacity&#39; and &#39;size&#39; of the sequence.
Definition: dds_seq.hh:290
bool reserve(uint32_t n)
Set the capacity of the sequence.
Definition: dds_seq.hh:250
sequence()
construct an empty sequence
Definition: dds_seq.hh:192
T & at(uint32_t n)
Definition: dds_seq.hh:331
bool empty() const
test if the sequence is empty
Definition: dds_seq.hh:240
bool push_back(const T &v)
Definition: dds_seq.hh:379
uint32_t capacity() const
Returns the current capacity (number of elements) of the sequence. The equation "size <= capacity" is...
Definition: dds_seq.hh:213
const T * buffer() const
Definition: dds_seq.hh:374
void swap(sequence &x)
Definition: dds_seq.hh:400

© 2009-2020 Twin Oaks Computing, Inc
Castle Rock, CO 80104
All rights reserved.