1#ifndef INC_CircularQueue_hpp__ 2#define INC_CircularQueue_hpp__ 3 4/* ANTLR Translator Generator 5 * Project led by Terence Parr at http://www.jGuru.com 6 * Software rights: http://www.antlr.org/license.html 7 * 8 * $Id: //depot/code/org.antlr/release/antlr-2.7.7/lib/cpp/antlr/CircularQueue.hpp#2 $ 9 */ 10 11#include <antlr/config.hpp> 12#include <antlr/Token.hpp> 13#include <vector> 14#include <cassert> 15 16#ifdef ANTLR_CXX_SUPPORTS_NAMESPACE 17namespace antlr { 18#endif 19 20// Resize every 5000 items 21#define OFFSET_MAX_RESIZE 5000 22 23template <class T> 24class ANTLR_API CircularQueue { 25public: 26 CircularQueue() 27 : storage() 28 , m_offset(0) 29 { 30 } 31 ~CircularQueue() 32 { 33 } 34 35 /// Clear the queue 36 inline void clear( void ) 37 { 38 m_offset = 0; 39 storage.clear(); 40 } 41 42 /// @todo this should use at or should have a check 43 inline T elementAt( size_t idx ) const 44 { 45 return storage[idx+m_offset]; 46 } 47 void removeFirst() 48 { 49 if (m_offset >= OFFSET_MAX_RESIZE) 50 { 51 storage.erase( storage.begin(), storage.begin() + m_offset + 1 ); 52 m_offset = 0; 53 } 54 else 55 ++m_offset; 56 } 57 inline void removeItems( size_t nb ) 58 { 59 // it would be nice if we would not get called with nb > entries 60 // (or to be precise when entries() == 0) 61 // This case is possible when lexer/parser::recover() calls 62 // consume+consumeUntil when the queue is empty. 63 // In recover the consume says to prepare to read another 64 // character/token. Then in the subsequent consumeUntil the 65 // LA() call will trigger 66 // syncConsume which calls this method *before* the same queue 67 // has been sufficiently filled. 68 if( nb > entries() ) 69 nb = entries(); 70 71 if (m_offset >= OFFSET_MAX_RESIZE) 72 { 73 storage.erase( storage.begin(), storage.begin() + m_offset + nb ); 74 m_offset = 0; 75 } 76 else 77 m_offset += nb; 78 } 79 inline void append(const T& t) 80 { 81 storage.push_back(t); 82 } 83 inline size_t entries() const 84 { 85 return storage.size() - m_offset; 86 } 87 88private: 89 ANTLR_USE_NAMESPACE(std)vector<T> storage; 90 size_t m_offset; 91 92 CircularQueue(const CircularQueue&); 93 const CircularQueue& operator=(const CircularQueue&); 94}; 95 96#ifdef ANTLR_CXX_SUPPORTS_NAMESPACE 97} 98#endif 99 100#endif //INC_CircularQueue_hpp__ 101