Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: orxonox.OLD/orxonox/branches/chris/src/list.h @ 2664

Last change on this file since 2664 was 2058, checked in by chris, 20 years ago

orxonox/branches/chris: Trunk remerged into my branch started on SDL reconfiguration

File size: 6.9 KB
Line 
1/*!
2  \file list.h
3  \brief Contains a template for a doubly linked list
4*/
5
6#ifndef LIST_H
7#define LIST_H
8
9#include "stdlib.h"
10
11//! An enum to list all the modes available when adding an object to a List
12enum ADDMODE {LIST_ADD_NEXT, LIST_ADD_PREV, LIST_ADD_FIRST, LIST_ADD_LAST};
13//! An enum to list the two searching directions available when removing an object from a List
14enum FINDMODE {LIST_FIND_BW, LIST_FIND_FW};
15
16//! A generic doubly linked list
17template<class T> class List
18{
19  T* object;
20  List<T>* next;
21  List<T>* prev;
22  bool bReference;
23 
24 public:
25  List (T* obj, List<T>* n, List<T>* p, bool bRef);
26  ~List ();
27 
28  int add (T* obj, ADDMODE mode, bool bRef);
29  T* get_object();
30  List<T>* get_next ();
31  List<T>* get_previous ();
32  List<T>* get_last ();
33  List<T>* get_first ();
34  void set_next (List<T>* ptr);
35  void set_prev (List<T>* ptr);
36  int remove (T* obj, FINDMODE mode);
37};
38
39/**
40  \brief Standard constructor
41 
42  Call this without any parameters to generate a new List which can be filled with content.
43  DO NOT create a List element that contains an object on your own, you'll lose the data
44  contained in that object and will have trouble removing the list from your memory.
45*/
46template<class T>
47List<T>::List (T* obj = NULL, List<T>* n = NULL, List<T>* p = NULL, bool bRef = false)
48{
49  object = obj;
50  next = n;
51  prev = p;
52  bReference = bRef;
53}
54
55/**
56  \brief Standard destructor
57 
58  Call this on the initially generated base List element to remove the whole List from the memory.
59  You can safely do this to any List element you want without messing up the rest of the List, but keep in mind
60  that the contained object will be deleted as well when bRef had been set to false.
61*/
62template<class T>
63List<T>::~List ()
64{
65  if (object == NULL) // deleted foot node => disband the list
66  {
67    while( next != NULL)
68    {
69      delete next;
70    }
71    while( prev != NULL)
72    {
73      delete prev;
74    }
75  }
76  else
77  {
78    if (prev != NULL) prev->set_next (next);
79    if (next != NULL) next->set_prev (prev);
80    if (!bReference) delete object;
81  }
82}
83 
84/**
85  \brief Add an object to the List
86  \param obj: A pointer to an allocated object
87  \param mode: A Value of ADDMODE (default: LIST_ADD_NEXT)
88  \param bRef: Sets whether the element is serving as a storage point or a simple listing (default: false)
89  \return 0 if the operation succeded, -1 if the element could not be added
90 
91  This adds a new List element to the chain. The mode parameter can be used to specify
92  the location where the element should be added. LIST_ADD_NEXT will add the new element directly
93  after the base element. LIST_ADD_PREV will add the new element directly before the base element.
94  LIST_ADD_FIRST will add the element at the beginning of the List whereas LIST_ADD_LAST will add
95  it to the end of the chain. If the bRef parameter is set to true, the object pointer will not be deleted
96  when the element containing that object is deleted, thus the List can be used for temporary listings as
97  well as permanent data storage.
98*/
99template<class T> 
100int List<T>::add (T* obj, ADDMODE mode = LIST_ADD_NEXT, bool bRef = false)
101{
102  List<T>* p;
103  if( obj == NULL) return -1;
104  switch (mode)
105  {
106    case LIST_ADD_NEXT:
107      p = new List<T>( obj, next, this, bRef);
108      if( next != NULL) next->set_prev (p);
109      next = p;
110      break;
111    case LIST_ADD_PREV:
112      p = new List<T>( obj, this, prev, bRef);
113      if( prev != NULL) prev->set_next (p);
114      prev = p;
115      break;
116    case LIST_ADD_FIRST:
117      if (prev == NULL) prev = new List<T> (obj, this, NULL, bRef);
118      else return prev->add (obj, mode, bRef);
119      break;
120    case LIST_ADD_LAST:
121      if (next == NULL) next = new List<T> (obj, NULL, this, bRef);
122      else return next->add (obj, mode, bRef);
123      break;
124    default:
125        return -1;
126      break;
127  }
128  return 0;
129}
130
131/**
132  \brief Get the next element of the List
133  \return The List element after the current List element
134*/
135template<class T>
136List<T>* List<T>::get_next ()
137{
138  return next;
139}
140 
141/**
142  \brief Get the previous element of the List
143  \return The List element before the current List element
144*/
145template<class T>
146List<T>* List<T>::get_previous ()
147{
148  return prev;
149}
150
151/**
152  \brief Get the last element of the List
153  \return The last List element
154*/
155template<class T>
156List<T>* List<T>::get_last ()
157{
158  if (next == NULL) return this;
159  else return next->get_last();
160}
161
162/**
163  \brief Get the first element of the List
164  \return The first List element
165*/
166template<class T>
167List<T>* List<T>::get_first ()
168{
169  if (prev == NULL) return this;
170  else return prev->get_first();
171}
172
173/**
174  \brief Removes a certain element from the List
175  \param obj: A pointer to the object that should be removed
176  \param mode: A value of FINDMODE
177  \return 0 if the element was found and removed, -1 if the element was not found
178 
179  This searches the part of the List specified with mode for the object in question.
180  When the object is found it is deleted and the List element is removed from the chain.
181  If mode is LIST_FIND_FW all elements AFTER the base element are searched, if mode is
182  LIST_FIND_BW all elements BEFORE the base element are searched. Note that the object
183  contained within the List element is NOT deleted when bRef was set to true.
184*/
185template<class T>
186int List<T>::remove (T* obj, FINDMODE mode = LIST_FIND_FW)
187{
188  if (obj == NULL) return -1;
189  else
190  {
191    switch (mode)
192    {
193      case LIST_FIND_BW:
194        if (prev == NULL) return -1;
195        else
196        {
197          if( prev->get_object() == obj)
198          {
199            delete prev;
200          }
201          else
202          {
203            return prev->remove( obj, mode);
204          }
205        }
206        break;
207      case LIST_FIND_FW:
208        if (next == NULL) return -1;
209        else
210        {
211          if( next->get_object() == obj)
212          {
213            delete next;
214          }
215          else
216          {
217            return next->remove( obj, mode);
218          }
219        }
220        break;
221      default:
222        return -1;
223    }
224  }
225  return 0;
226}
227
228/**
229  \brief Set the next element of a List element
230  \param ptr: A pointer to the new next element
231   
232  Sets the next element of a List element... Better not touch this, it can really mess up a List.
233*/
234template<class T>
235void List<T>::set_next (List<T>* ptr)
236{
237  next = ptr;
238}
239
240/**
241  \brief Set the prev element of a List element
242  \param ptr: A pointer to the new previous element
243   
244  Sets the previous element of a List element... Better not touch this, it can really mess up a List.
245*/
246template<class T>
247void List<T>::set_prev (List<T>* ptr)
248{
249  prev = ptr;
250}
251
252/**
253  \brief Get the pointer to the object the element is containing
254  \return The contained object (will be NULL if called on the base element).
255*/
256template<class T>
257T* List<T>::get_object()
258{
259  return object;
260}
261
262#endif
Note: See TracBrowser for help on using the repository browser.