LinkList.h 7.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344
  1. /*
  2. ===========================================================================
  3. Doom 3 GPL Source Code
  4. Copyright (C) 1999-2011 id Software LLC, a ZeniMax Media company.
  5. This file is part of the Doom 3 GPL Source Code (?Doom 3 Source Code?).
  6. Doom 3 Source Code is free software: you can redistribute it and/or modify
  7. it under the terms of the GNU General Public License as published by
  8. the Free Software Foundation, either version 3 of the License, or
  9. (at your option) any later version.
  10. Doom 3 Source Code is distributed in the hope that it will be useful,
  11. but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. GNU General Public License for more details.
  14. You should have received a copy of the GNU General Public License
  15. along with Doom 3 Source Code. If not, see <http://www.gnu.org/licenses/>.
  16. In addition, the Doom 3 Source Code is also subject to certain additional terms. You should have received a copy of these additional terms immediately following the terms and conditions of the GNU General Public License which accompanied the Doom 3 Source Code. If not, please request a copy in writing from id Software at the address below.
  17. If you have questions concerning this license or the applicable additional terms, you may contact in writing id Software LLC, c/o ZeniMax Media Inc., Suite 120, Rockville, Maryland 20850 USA.
  18. ===========================================================================
  19. */
  20. #ifndef __LINKLIST_H__
  21. #define __LINKLIST_H__
  22. /*
  23. ==============================================================================
  24. idLinkList
  25. Circular linked list template
  26. ==============================================================================
  27. */
  28. template< class type >
  29. class idLinkList {
  30. public:
  31. idLinkList();
  32. ~idLinkList();
  33. bool IsListEmpty( void ) const;
  34. bool InList( void ) const;
  35. int Num( void ) const;
  36. void Clear( void );
  37. void InsertBefore( idLinkList &node );
  38. void InsertAfter( idLinkList &node );
  39. void AddToEnd( idLinkList &node );
  40. void AddToFront( idLinkList &node );
  41. void Remove( void );
  42. type * Next( void ) const;
  43. type * Prev( void ) const;
  44. type * Owner( void ) const;
  45. void SetOwner( type *object );
  46. idLinkList * ListHead( void ) const;
  47. idLinkList * NextNode( void ) const;
  48. idLinkList * PrevNode( void ) const;
  49. private:
  50. idLinkList * head;
  51. idLinkList * next;
  52. idLinkList * prev;
  53. type * owner;
  54. };
  55. /*
  56. ================
  57. idLinkList<type>::idLinkList
  58. Node is initialized to be the head of an empty list
  59. ================
  60. */
  61. template< class type >
  62. idLinkList<type>::idLinkList() {
  63. owner = NULL;
  64. head = this;
  65. next = this;
  66. prev = this;
  67. }
  68. /*
  69. ================
  70. idLinkList<type>::~idLinkList
  71. Removes the node from the list, or if it's the head of a list, removes
  72. all the nodes from the list.
  73. ================
  74. */
  75. template< class type >
  76. idLinkList<type>::~idLinkList() {
  77. Clear();
  78. }
  79. /*
  80. ================
  81. idLinkList<type>::IsListEmpty
  82. Returns true if the list is empty.
  83. ================
  84. */
  85. template< class type >
  86. bool idLinkList<type>::IsListEmpty( void ) const {
  87. return head->next == head;
  88. }
  89. /*
  90. ================
  91. idLinkList<type>::InList
  92. Returns true if the node is in a list. If called on the head of a list, will always return false.
  93. ================
  94. */
  95. template< class type >
  96. bool idLinkList<type>::InList( void ) const {
  97. return head != this;
  98. }
  99. /*
  100. ================
  101. idLinkList<type>::Num
  102. Returns the number of nodes in the list.
  103. ================
  104. */
  105. template< class type >
  106. int idLinkList<type>::Num( void ) const {
  107. idLinkList<type> *node;
  108. int num;
  109. num = 0;
  110. for( node = head->next; node != head; node = node->next ) {
  111. num++;
  112. }
  113. return num;
  114. }
  115. /*
  116. ================
  117. idLinkList<type>::Clear
  118. If node is the head of the list, clears the list. Otherwise it just removes the node from the list.
  119. ================
  120. */
  121. template< class type >
  122. void idLinkList<type>::Clear( void ) {
  123. if ( head == this ) {
  124. while( next != this ) {
  125. next->Remove();
  126. }
  127. } else {
  128. Remove();
  129. }
  130. }
  131. /*
  132. ================
  133. idLinkList<type>::Remove
  134. Removes node from list
  135. ================
  136. */
  137. template< class type >
  138. void idLinkList<type>::Remove( void ) {
  139. prev->next = next;
  140. next->prev = prev;
  141. next = this;
  142. prev = this;
  143. head = this;
  144. }
  145. /*
  146. ================
  147. idLinkList<type>::InsertBefore
  148. Places the node before the existing node in the list. If the existing node is the head,
  149. then the new node is placed at the end of the list.
  150. ================
  151. */
  152. template< class type >
  153. void idLinkList<type>::InsertBefore( idLinkList &node ) {
  154. Remove();
  155. next = &node;
  156. prev = node.prev;
  157. node.prev = this;
  158. prev->next = this;
  159. head = node.head;
  160. }
  161. /*
  162. ================
  163. idLinkList<type>::InsertAfter
  164. Places the node after the existing node in the list. If the existing node is the head,
  165. then the new node is placed at the beginning of the list.
  166. ================
  167. */
  168. template< class type >
  169. void idLinkList<type>::InsertAfter( idLinkList &node ) {
  170. Remove();
  171. prev = &node;
  172. next = node.next;
  173. node.next = this;
  174. next->prev = this;
  175. head = node.head;
  176. }
  177. /*
  178. ================
  179. idLinkList<type>::AddToEnd
  180. Adds node at the end of the list
  181. ================
  182. */
  183. template< class type >
  184. void idLinkList<type>::AddToEnd( idLinkList &node ) {
  185. InsertBefore( *node.head );
  186. }
  187. /*
  188. ================
  189. idLinkList<type>::AddToFront
  190. Adds node at the beginning of the list
  191. ================
  192. */
  193. template< class type >
  194. void idLinkList<type>::AddToFront( idLinkList &node ) {
  195. InsertAfter( *node.head );
  196. }
  197. /*
  198. ================
  199. idLinkList<type>::ListHead
  200. Returns the head of the list. If the node isn't in a list, it returns
  201. a pointer to itself.
  202. ================
  203. */
  204. template< class type >
  205. idLinkList<type> *idLinkList<type>::ListHead( void ) const {
  206. return head;
  207. }
  208. /*
  209. ================
  210. idLinkList<type>::Next
  211. Returns the next object in the list, or NULL if at the end.
  212. ================
  213. */
  214. template< class type >
  215. type *idLinkList<type>::Next( void ) const {
  216. if ( !next || ( next == head ) ) {
  217. return NULL;
  218. }
  219. return next->owner;
  220. }
  221. /*
  222. ================
  223. idLinkList<type>::Prev
  224. Returns the previous object in the list, or NULL if at the beginning.
  225. ================
  226. */
  227. template< class type >
  228. type *idLinkList<type>::Prev( void ) const {
  229. if ( !prev || ( prev == head ) ) {
  230. return NULL;
  231. }
  232. return prev->owner;
  233. }
  234. /*
  235. ================
  236. idLinkList<type>::NextNode
  237. Returns the next node in the list, or NULL if at the end.
  238. ================
  239. */
  240. template< class type >
  241. idLinkList<type> *idLinkList<type>::NextNode( void ) const {
  242. if ( next == head ) {
  243. return NULL;
  244. }
  245. return next;
  246. }
  247. /*
  248. ================
  249. idLinkList<type>::PrevNode
  250. Returns the previous node in the list, or NULL if at the beginning.
  251. ================
  252. */
  253. template< class type >
  254. idLinkList<type> *idLinkList<type>::PrevNode( void ) const {
  255. if ( prev == head ) {
  256. return NULL;
  257. }
  258. return prev;
  259. }
  260. /*
  261. ================
  262. idLinkList<type>::Owner
  263. Gets the object that is associated with this node.
  264. ================
  265. */
  266. template< class type >
  267. type *idLinkList<type>::Owner( void ) const {
  268. return owner;
  269. }
  270. /*
  271. ================
  272. idLinkList<type>::SetOwner
  273. Sets the object that this node is associated with.
  274. ================
  275. */
  276. template< class type >
  277. void idLinkList<type>::SetOwner( type *object ) {
  278. owner = object;
  279. }
  280. #endif /* !__LINKLIST_H__ */