3 * ===============================================================
4 * SourceMod (C)2004-2007 AlliedModders LLC. All rights reserved.
5 * ===============================================================
7 * This file is not open source and may not be copied without explicit
8 * written permission of AlliedModders LLC. This file may not be redistributed
9 * in whole or significant part.
10 * For information, see LICENSE.txt or http://www.sourcemod.net/license.php
16 #ifndef _INCLUDE_SM_QUEUE_H
17 #define _INCLUDE_SM_QUEUE_H
23 using namespace SourceHook;
26 A circular, doubly-linked List with one sentinel node
30 m_Head->next = m_Head;
31 m_Head->prev = m_Head;
52 friend class iterator;
61 // Initializes the sentinel node.
62 QueueNode *_Initialize()
64 QueueNode *n = (QueueNode *)malloc(sizeof(QueueNode));
70 Queue() : m_Head(_Initialize()), m_Size(0)
74 Queue(const Queue &src) : m_Head(_Initialize()), m_Size(0)
77 for (iter=src.begin(); iter!=src.end(); iter++)
87 // Don't forget to free the sentinel
94 while (!m_FreeNodes.empty())
96 free(m_FreeNodes.front());
101 void push(const T &obj)
105 if (m_FreeNodes.empty())
107 node = (QueueNode *)malloc(sizeof(QueueNode));
109 node = m_FreeNodes.front();
113 /* Copy the object */
114 new (&node->obj) T(obj);
116 /* Install into the Queue */
117 node->prev = m_Head->prev;
119 m_Head->prev->next = node;
132 QueueNode *node = m_Head->next;
134 m_Head->next = m_Head;
135 m_Head->prev = m_Head;
137 // Iterate through the nodes until we find g_Head (the sentinel) again
138 while (node != m_Head)
142 m_FreeNodes.push(node);
150 return (m_Size == 0);
156 CStack<QueueNode *> m_FreeNodes;
166 iterator(const Queue &src)
170 iterator(QueueNode *n) : m_This(n)
173 iterator(const iterator &where)
175 m_This = where.m_This;
178 iterator & operator--()
181 m_This = m_This->prev;
185 iterator operator--(int)
189 m_This = m_This->prev;
194 iterator & operator++()
197 m_This = m_This->next;
201 iterator operator++(int)
205 m_This = m_This->next;
209 const T & operator * () const
220 return &(m_This->obj);
222 const T * operator -> () const
224 return &(m_This->obj);
227 bool operator != (const iterator &where) const
229 return (m_This != where.m_This);
231 bool operator ==(const iterator &where) const
233 return (m_This == where.m_This);
239 iterator begin() const
241 return iterator(m_Head->next);
246 return iterator(m_Head);
249 iterator erase(iterator &where)
251 QueueNode *pNode = where.m_This;
252 iterator iter(where);
256 // Works for all cases: empty Queue, erasing first element, erasing tail, erasing in the middle...
257 pNode->prev->next = pNode->next;
258 pNode->next->prev = pNode->prev;
261 m_FreeNodes.push(pNode);
267 void remove(const T & obj)
270 for (b=begin(); b!=end(); b++)
279 template <typename U>
280 iterator find(const U & equ) const
283 for (iter=begin(); iter!=end(); iter++)
285 if ( (*iter) == equ )
292 Queue & operator =(const Queue &src)
296 for (iter=src.begin(); iter!=src.end(); iter++)
298 push_back( (*iter) );
305 iterator i = begin();
312 iterator iter = begin();
317 #endif //_INCLUDE_SM_QUEUE_H