xsens_fifoqueue.h

Go to the documentation of this file.
00001 #ifndef _CMT_MONOLITHIC
00002 /*! \file
00003         \brief        Contains the FIFO queue interface and implementation (inline)
00004 
00005         \section FileCopyright Copyright Notice 
00006         Copyright (C) Xsens Technologies B.V., 2006.  All rights reserved.
00007 
00008         This source code is intended for use only by Xsens Technologies BV and
00009         those that have explicit written permission to use it from
00010         Xsens Technologies BV.
00011 
00012         THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY
00013         KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
00014         IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
00015         PARTICULAR PURPOSE.
00016 
00017         \section FileChangelog        Changelog
00018 
00019         \par 2006-05-03, v0.0.1
00020         \li Job Mulder:        Created Cmtfifoqueue.h
00021 
00022         \par 2006-07-21, v0.1.0
00023         \li Job Mulder:        Updated file for release 0.1.0
00024 */
00025 #endif
00026 #ifndef _FIFOQUEUE_H_2006_05_03
00027 #define _FIFOQUEUE_H_2006_05_03
00028 
00029 
00030 namespace xsens {
00031 
00032 //////////////////////////////////////////////////////////////////////////////////////////
00033 
00034 /*! \brief A FIFO queue with limited length (cyclic).
00035 
00036         The class is based on the STL queue class, but has a limited size. If more items are
00037         inserted than would fit, the oldest item is overwritten. The class can only handle 
00038         pointer types.
00039 */
00040 template <class T, bool E=true>
00041 class FifoQueue {
00042 protected:
00043         size_t m_maxCount;
00044         size_t m_currentCount;
00045         size_t m_first;
00046         bool m_deleteOnOverwrite;
00047 
00048         T*        m_list;
00049 public:
00050         typedef T                value_type;                //!< The type of the value stored in this queue.
00051         typedef size_t        size_type;                //!< The type of a 'size' value.
00052 
00053         //! Create an empty queue with capacity size.
00054         FifoQueue(size_type size=16, bool delOnOverwrite = true)
00055         {
00056                 if (size > 0)
00057                         m_maxCount = size;
00058                 else
00059                         m_maxCount = 1;
00060                 m_list = new T[m_maxCount];
00061                 m_currentCount = 0;
00062                 m_first = 0;
00063                 m_deleteOnOverwrite = delOnOverwrite;
00064         }
00065         
00066         //! The copy constructor.
00067         template <bool E2>
00068         FifoQueue(const FifoQueue<T,E2>& q)
00069         {
00070                 m_maxCount = q.m_maxCount;
00071                 m_list = new T[m_maxCount];
00072                 m_currentCount = q.m_currentCount;
00073                 m_deleteOnOverwrite = q.m_deleteOnOverwrite;
00074                 m_first = 0;
00075                 for (size_t i = 0;i<m_currentCount;++i)
00076                         m_list[i] = q.m_list[(i+q.m_first) % m_maxCount];
00077         }
00078         
00079         void eraseAndClear(void)
00080         {
00081                 for (size_t i = 0;i<m_currentCount;++i)
00082                         delete m_list[(i+m_first) % m_maxCount];
00083                 m_currentCount = 0;
00084                 m_first = 0;
00085         }
00086 
00087         //! The destructor.
00088         ~FifoQueue()
00089         {
00090                 if (E)
00091                         eraseAndClear();
00092                 m_maxCount = 0;
00093                 delete[] m_list;
00094         }
00095 
00096         //! The assignment operator.
00097         template <bool E2>
00098         FifoQueue<T,E>& operator=(const FifoQueue<T,E2>& q)
00099         {
00100                 if (m_maxCount != q.m_maxCount)
00101                 {
00102                         delete[] m_list;
00103                         m_maxCount = q.m_maxCount;
00104                         m_list = new T[m_maxCount];
00105                 }
00106                 m_currentCount = q.m_currentCount;
00107                 m_first = 0;
00108                 for (size_t i = 0;i<m_currentCount;++i)
00109                         m_list[i] = q.m_list[(i+q.m_first) % m_maxCount];
00110 
00111                 return *this;
00112         }
00113         
00114         //! Resize the queue, note that this function clears the queue.
00115         void resize(const size_t size)
00116         {
00117                 if (E)
00118                         eraseAndClear();
00119                 delete[] m_list;
00120                 if (size > 0)
00121                         m_maxCount = size;
00122                 else
00123                         m_maxCount = 1;
00124                 m_list = new T[m_maxCount];
00125                 m_currentCount = 0;
00126                 m_first = 0;
00127         }
00128 
00129         //! Return true if the queue is empty.
00130         bool empty() const
00131         {
00132                 return (m_currentCount == 0);
00133         }
00134         
00135         //! Return the maximum number of elements in the queue.
00136         size_type size() const
00137         {
00138                 return m_maxCount;
00139         }
00140         
00141         //! Return the number of elements currnetly in the queue.
00142         size_type length() const
00143         {
00144                 return m_currentCount;
00145         }
00146 
00147         //! Return the oldest element in the queue.
00148         value_type& front()
00149         {
00150                 return m_list[m_first];
00151         }
00152         
00153         //! Return the oldest element in the queue.
00154         const value_type& front() const
00155         {
00156                 return m_list[m_first];
00157         }
00158         
00159         //! Return the newest element in the queue.
00160         value_type& back()
00161         {
00162                 return m_list[(m_first + m_currentCount - 1) % m_maxCount];
00163         }
00164         
00165         //! Return the newest element in the queue.
00166         const value_type& back() const
00167         {
00168                 return m_list[(m_first + m_currentCount - 1) % m_maxCount];
00169         }
00170         
00171         //! Insert x at the back of the queue.
00172         void push(const value_type& x)
00173         {
00174                 if (m_currentCount == m_maxCount)
00175                 {
00176                         if (m_deleteOnOverwrite)
00177                                 delete (m_list[m_first]);
00178                         
00179                         m_list[m_first] = x;
00180                         m_first = (m_first+1) % m_maxCount;
00181                 }
00182                 else
00183                 {
00184                         m_list[(m_first + m_currentCount++) % m_maxCount] = x;
00185                 }
00186         }
00187         
00188         //! Remove the element at the front of the queue.
00189         void pop(void)
00190         {
00191                 m_first = (m_first+1) % m_maxCount;
00192                 --m_currentCount;
00193         }
00194 
00195         //! Remove the element at the back of the queue.
00196         void popBack(void)
00197         {
00198                 --m_currentCount;
00199         }
00200 
00201         //! Return the index'th oldest item from the queue
00202         const value_type& operator[] (size_t index) const
00203         {
00204                 if (index >= m_currentCount)
00205                         return m_list[(m_first + m_currentCount - 1) % m_maxCount];
00206                 else
00207                         return m_list[(m_first + index) % m_maxCount];
00208         }
00209 
00210         //! Return the index'th oldest item from the queue
00211         value_type& operator[] (size_t index)
00212         {
00213                 if (index >= m_currentCount)
00214                         return m_list[(m_first + m_currentCount - 1) % m_maxCount];
00215                 else
00216                         return m_list[(m_first + index) % m_maxCount];
00217         }
00218 
00219         void clear(void)
00220         {
00221                 m_currentCount = 0;
00222                 m_first = 0;
00223         }
00224 
00225         void remove(size_t index)
00226         {
00227                 if (index >= m_currentCount)
00228                         return;
00229                 if (index == 0)
00230                         pop();
00231                 else
00232                 {
00233                         --m_currentCount;
00234                         for (size_t i=index;i<m_currentCount;++i)
00235                                 m_list[(m_first + i) % m_maxCount] = m_list[(1 + m_first + i) % m_maxCount];
00236                 }
00237         }
00238 };
00239 
00240 
00241 //////////////////////////////////////////////////////////////////////////////////////////
00242 
00243 /*! \brief A FIFO queue with limited length (cyclic).
00244 
00245         The class is based on the STL queue class, but has a limited size. If more items are
00246         inserted than would fit, the oldest item is overwritten. The class can only handle 
00247         non-pointer types.
00248 */
00249 template <class T>
00250 class FifoQueueBasic {
00251 protected:
00252         size_t m_maxCount;
00253         size_t m_currentCount;
00254         size_t m_first;
00255 
00256         T*        m_list;
00257 public:
00258         typedef T                value_type;                //!< The type of the value stored in this queue.
00259         typedef size_t        size_type;                //!< The type of a 'size' value.
00260 
00261         //! Create an empty queue with capacity 'size'.
00262         FifoQueueBasic(size_type size=16)
00263         {
00264                 if (size > 0)
00265                         m_maxCount = size;
00266                 else
00267                         m_maxCount = 1;
00268                 m_list = new T[m_maxCount];
00269                 m_currentCount = 0;
00270                 m_first = 0;
00271         }
00272         
00273         //! The copy constructor.
00274         FifoQueueBasic(const FifoQueueBasic<T>& q)
00275         {
00276                 m_maxCount = q.m_maxCount;
00277                 m_list = new T[m_maxCount];
00278                 m_currentCount = q.m_currentCount;
00279                 m_first = 0;
00280                 for (size_t i = 0;i<m_currentCount;++i)
00281                         m_list[i] = q.m_list[(i+q.m_first) % m_maxCount];
00282         }
00283         
00284         void eraseAndClear(void)
00285         {
00286                 for (size_t i = 0;i<m_currentCount;++i)
00287                         delete m_list[(i+m_first) % m_maxCount];
00288                 m_currentCount = 0;
00289                 m_first = 0;
00290         }
00291 
00292         //! The destructor.
00293         ~FifoQueueBasic()
00294         {
00295                 m_maxCount = 0;
00296                 delete[] m_list;
00297         }
00298 
00299         //! The assignment operator.
00300         FifoQueueBasic<T>& operator=(const FifoQueueBasic<T>& q)
00301         {
00302                 if (m_maxCount != q.m_maxCount)
00303                 {
00304                         delete[] m_list;
00305                         m_maxCount = q.m_maxCount;
00306                         m_list = new T[m_maxCount];
00307                 }
00308                 m_currentCount = q.m_currentCount;
00309                 m_first = 0;
00310                 for (size_t i = 0;i<m_currentCount;++i)
00311                         m_list[i] = q.m_list[(i+q.m_first) % m_maxCount];
00312 
00313                 return *this;
00314         }
00315         
00316         //! Resize the queue, note that this function clears the queue.
00317         void resize(const size_t size)
00318         {
00319                 delete[] m_list;
00320                 if (size > 0)
00321                         m_maxCount = size;
00322                 else
00323                         m_maxCount = 1;
00324                 m_list = new T[m_maxCount];
00325                 m_currentCount = 0;
00326                 m_first = 0;
00327         }
00328 
00329         //! Return true if the queue is empty.
00330         bool empty() const
00331         {
00332                 return (m_currentCount == 0);
00333         }
00334         
00335         //! Return the maximum number of elements in the queue.
00336         size_type size() const
00337         {
00338                 return m_maxCount;
00339         }
00340         
00341         //! Return the number of elements currently in the queue.
00342         size_type length() const
00343         {
00344                 return m_currentCount;
00345         }
00346 
00347         //! Return the oldest element in the queue.
00348         value_type& front()
00349         {
00350                 return m_list[m_first];
00351         }
00352         
00353         //! Return the oldest element in the queue.
00354         const value_type& front() const
00355         {
00356                 return m_list[m_first];
00357         }
00358         
00359         //! Return the newest element in the queue.
00360         value_type& back()
00361         {
00362                 return m_list[(m_first + m_currentCount - 1) % m_maxCount];
00363         }
00364         
00365         //! Return the newest element in the queue.
00366         const value_type& back() const
00367         {
00368                 return m_list[(m_first + m_currentCount - 1) % m_maxCount];
00369         }
00370         
00371         //! Insert x at the back of the queue.
00372         void push(const value_type& x)
00373         {
00374                 if (m_currentCount == m_maxCount)
00375                 {
00376                         m_list[m_first] = x;
00377                         m_first = (m_first+1) % m_maxCount;
00378                 }
00379                 else
00380                 {
00381                         m_list[(m_first + m_currentCount++) % m_maxCount] = x;
00382                 }
00383         }
00384 
00385         //! Insert x at the front of the queue (LIFO operation).
00386         void push_front(const value_type& x)
00387         {
00388                 m_first = (m_first+m_maxCount-1)%m_maxCount;
00389                 if (m_currentCount == 0)
00390                         m_first = 0;
00391                 m_list[m_first] = x;
00392                 if (m_currentCount < m_maxCount)
00393                         ++m_currentCount;
00394         }
00395 
00396         //! Remove the element at the front of the queue.
00397         void pop(void)
00398         {
00399                 if (m_currentCount > 0)
00400                 {
00401                         m_first = (m_first+1) % m_maxCount;
00402                         --m_currentCount;
00403                 }
00404         }
00405 
00406         //! Remove the element at the back of the queue.
00407         void popBack(void)
00408         {
00409                 if (m_currentCount > 0)
00410                         --m_currentCount;
00411         }
00412 
00413         //! Return the index'th oldest item from the queue
00414         const value_type& operator[] (size_t index) const
00415         {
00416                 if (index >= m_currentCount)
00417                         return m_list[(m_first + m_currentCount - 1) % m_maxCount];
00418                 else
00419                         return m_list[(m_first + index) % m_maxCount];
00420         }
00421 
00422         //! Return the index'th oldest item from the queue
00423         value_type& operator[] (size_t index)
00424         {
00425                 if (index >= m_currentCount)
00426                         return m_list[(m_first + m_currentCount - 1) % m_maxCount];
00427                 else
00428                         return m_list[(m_first + index) % m_maxCount];
00429         }
00430 
00431         void clear(void)
00432         {
00433                 m_currentCount = 0;
00434                 m_first = 0;
00435         }
00436 
00437         void remove(size_t index)
00438         {
00439                 if (index >= m_currentCount)
00440                         return;
00441                 if (index == 0)
00442                         pop();
00443                 else
00444                 {
00445                         --m_currentCount;
00446                         for (size_t i=index;i<m_currentCount;++i)
00447                                 m_list[(m_first + i) % m_maxCount] = m_list[(1 + m_first + i) % m_maxCount];
00448                 }
00449         }
00450 };
00451 
00452 } // end of xsens namespace
00453 
00454 #endif        // _FIFOQUEUE_H_2006_05_03
Generated on Sun May 8 08:41:37 2011 for iLab Neuromorphic Vision Toolkit by  doxygen 1.6.3