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_SOURCEMOD_FASTLINK_H_
17 #define _INCLUDE_SOURCEMOD_FASTLINK_H_
24 friend class iterator;
30 unsigned int freeNode;
34 FastLink(unsigned int maxsize) : m_Size(0), m_FirstLink(0), m_FreeNodes(0), m_LastLink(0), m_UsableIndex(0)
37 m_Nodes = new FastLinkNode[m_MaxSize+1];
40 bool push_back(const T & obj)
42 unsigned int new_node = GetFreeIndex();
47 m_Nodes[new_node].obj = obj;
48 m_Nodes[new_node].next = 0;
51 m_Nodes[new_node].prev = 0;
52 m_FirstLink = new_node;
53 m_LastLink = new_node;
55 m_Nodes[new_node].prev = m_LastLink;
56 m_Nodes[m_LastLink].next = new_node;
57 m_LastLink = new_node;
67 unsigned int GetFreeIndex()
71 return m_Nodes[m_FreeNodes--].freeNode;
73 if (m_UsableIndex >= m_MaxSize)
84 friend class FastLink;
91 iterator(const FastLink *_link, unsigned int _position)
97 bool operator ==(const iterator &where) const
99 return (link == where.link && position == where.position);
101 bool operator !=(const iterator &where) const
103 return (link != where.link || position != where.position);
107 return link->m_Nodes[position].obj;
109 const T & operator *() const
111 return link->m_Nodes[position].obj;
113 iterator & operator++()
115 position = link->m_Nodes[position].next;
119 const FastLink *link;
120 unsigned int position;
123 iterator begin() const
125 return iterator(this, m_FirstLink);
129 return iterator(this, 0);
131 void remove(const T & obj)
133 for (iterator iter=begin(); iter!=end(); ++iter)
142 iterator erase(const iterator &where)
144 /* Whoa, this better be right! */
145 assert(where.link == this);
147 iterator iter(where.link, where.position);
150 unsigned int index = where.position;
152 /* Each case is different, we have no sentinel.
153 * CASE: We're the HEAD AND the TAIL */
154 if (index == m_FirstLink
155 && index == m_LastLink)
161 else if (index == m_FirstLink)
163 m_FirstLink = m_Nodes[index].next;
164 m_Nodes[m_FirstLink].prev = 0;
167 else if (index == m_LastLink)
169 m_LastLink = m_Nodes[index].prev;
170 m_Nodes[m_LastLink].next = 0;
172 /* We're in the middle! */
175 /* Patch forward reference */
176 m_Nodes[m_Nodes[index].next].prev = m_Nodes[index].prev;
177 /* Patch backward reference */
178 m_Nodes[m_Nodes[index].prev].next = m_Nodes[index].next;
181 /* Add us to the free list */
182 m_Nodes[++m_FreeNodes].freeNode = index;
188 #if defined MENU_DEBUG
194 unsigned int m_FirstLink;
195 unsigned int m_FreeNodes;
196 unsigned int m_LastLink;
197 unsigned int m_MaxSize;
198 unsigned int m_UsableIndex;
199 FastLinkNode *m_Nodes;
202 #endif //_INCLUDE_SOURCEMOD_FASTLINK_H_