aboutsummaryrefslogtreecommitdiff
path: root/src/ringbuffer.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/ringbuffer.h')
-rw-r--r--src/ringbuffer.h97
1 files changed, 97 insertions, 0 deletions
diff --git a/src/ringbuffer.h b/src/ringbuffer.h
new file mode 100644
index 0000000..be80e2f
--- /dev/null
+++ b/src/ringbuffer.h
@@ -0,0 +1,97 @@
1#ifndef BU_RING_BUFFER_H
2#define BU_RING_BUFFER_H
3
4#include <memory>
5#include "bu/exceptionbase.h"
6
7namespace Bu
8{
9 template<typename value, typename valuealloc=std::allocator<value> >
10 class RingBuffer
11 {
12 public:
13 RingBuffer( int nCapacity ) :
14 nCapacity( nCapacity ),
15 nStart( -1 ),
16 nEnd( -2 )
17 {
18 aData = va.allocate( nCapacity );
19 }
20
21 virtual ~RingBuffer()
22 {
23 for( int j = nStart; j < nEnd; j=(j+1%nCapacity) )
24 {
25 va.destroy( &aData[j] );
26 }
27 va.deallocate( aData, nCapacity );
28 }
29
30 int getCapacity()
31 {
32 return nCapacity;
33 }
34
35 bool isFilled()
36 {
37 return (nStart == nEnd);
38 }
39
40 bool isEmpty()
41 {
42 return (nStart == -1);
43 }
44
45 void enqueue( const value &v )
46 {
47 if( nStart == -1 )
48 {
49 nStart = 0;
50 nEnd = 1;
51 va.construct( &aData[0], v );
52 }
53 else if( nStart == nEnd )
54 {
55 throw ExceptionBase("Hey, it's full!");
56 }
57 else
58 {
59 va.construct( &aData[nEnd], v );
60 nEnd = (nEnd+1)%nCapacity;
61 }
62 }
63
64 value dequeue()
65 {
66 if( nStart == -1 )
67 {
68 throw ExceptionBase("No data");
69 }
70 else
71 {
72 value &v = aData[nStart];
73 va.destroy( &aData[nStart] );
74 nStart = (nStart+1)%nCapacity;
75 if( nStart == nEnd )
76 {
77 nStart = -1;
78 nEnd = -2;
79 }
80 return v;
81 }
82 }
83
84 value &operator[]( int nIndex )
85 {
86 return aData[(nIndex+nStart)%nCapacity];
87 }
88
89 private:
90 int nCapacity;
91 value *aData;
92 valuealloc va;
93 int nStart, nEnd;
94 };
95}
96
97#endif