Open
Graph Drawing
Framework

 v.2012.07
 

EList.h
Go to the documentation of this file.
1 /*
2  * $Revision: 2579 $
3  *
4  * last checkin:
5  * $Author: gutwenger $
6  * $Date: 2012-07-11 15:28:17 +0200 (Mi, 11. Jul 2012) $
7  ***************************************************************/
8 
96 #ifdef _MSC_VER
97 #pragma once
98 #endif
99 
100 #ifndef OGDF_ELIST_H
101 #define OGDF_ELIST_H
102 
103 namespace ogdf {
104 
105 // EStack forward declaration
106 template<typename S, typename E, E* S::*first, E* E::*next> class EStack;
107 // EListIterator forward declaration
108 template<typename E, E* E::*prev, E* E::*next> class EListIterator;
109 // EList forward declaration
110 template<typename L, typename E, int L::*numElem, E* L::*first, E* L::*last, E* E::*next, E* E::*prev> class EList;
111 
113 template<typename S, typename E, E* S::*first, E* E::*next>
114 class EStack
115 {
116 public:
118  static inline void init(S* pStack)
119  {
120  pStack->*first = 0;
121  }
122 
124  static inline void pop(S* pStack)
125  {
126  pStack->*first = pStack->*first->*next;
127  }
128 
130  static inline E* popRet(S* pStack)
131  {
132  E* res = pStack->*first;
133  pStack->*first = pStack->*first->*next;
134  return res;
135  }
136 
138  static inline void push(S* pStack, E* pElem)
139  {
140  pElem->*next = pStack->*first;
141  pStack->*first = pElem;
142  }
143 
145  static inline E* top(const S* pStack)
146  {
147  return pStack->*first;
148  }
149 
151  static inline bool empty(const S* pStack)
152  {
153  return (pStack->*first == 0);
154  }
155 };
156 
157 
159 template<typename E, E* E::*prev, E* E::*next>
161 {
162 public:
164  inline EListIterator( ) : m_ptr(0) {}
165 
167  inline EListIterator(E* ptr) : m_ptr(ptr) {}
168 
170  inline EListIterator(const EListIterator<E, prev, next>& other) : m_ptr(other.m_ptr) {}
171 
173  inline bool valid() const { return (m_ptr != 0); }
174 
176  inline bool operator==(const EListIterator<E, prev, next>& other) const { return m_ptr == other.m_ptr; }
177 
179  inline bool operator!=(const EListIterator<E, prev, next>& other) const { return m_ptr != other.m_ptr; }
180 
182  inline EListIterator<E, prev, next> succ() const { return m_ptr->*next; }
183 
185  inline EListIterator<E, prev, next> pred() const { return m_ptr->*prev; }
186 
188  //E& operator*() const { return *m_ptr; }
189 
191  E* operator*() const { return m_ptr; }
192 
195  {
196  m_ptr = other.m_ptr;
197  return *this;
198  }
199 
202  {
203  m_ptr = m_ptr->*next;
204  return *this;
205  }
206 
209  {
210  EListIterator<E, prev, next> it = *this;
211  m_ptr = m_ptr->*next;
212  return it;
213  }
214 
217  {
218  m_ptr = m_ptr->*prev;
219  return *this;
220  }
221 
224  {
225  EListIterator<E, prev, next> it = *this;
226  m_ptr = m_ptr->*prev;
227  return it;
228  }
229 
230 private:
232  E* m_ptr;
233 };
234 
235 
237 template<
238  typename L,
239  typename E,
240  int L::*numElem,
241  E* L::*first,
242  E* L::*last,
243  E* E::*next,
244  E* E::*prev
245 >
246 class EList
247 {
248 public:
251 
253  static inline void init(L* pList)
254  {
255  pList->*first = 0;
256  pList->*last = 0;
257  pList->*numElem = 0;
258  }
259 
261  static inline int size(const L* pList) { return (pList->*numElem); }
262 
264  static inline bool empty(const L* pList) { return (pList->*first == 0); }
265 
267  static inline E* front(const L* pList) { return pList->*first; }
268 
270  static inline E* back(const L* pList) { return pList->*last; }
271 
273  static inline iterator pushBack(L* pList, E* elem)
274  {
275  elem->*next = 0;
276  elem->*prev = pList->*last;
277  if (pList->*last)
278  pList->*last = pList->*last->*next = elem;
279  else
280  pList->*last = pList->*first = elem;
281 
282  (pList->*numElem)++;
283  return iterator(elem);
284  }
285 
287  static inline iterator pushFront(L* pList, E* elem)
288  {
289  elem->*next = pList->*first;
290  elem->*prev = 0;
291 
292  if (pList->*first)
293  pList->*first = pList->*first->*prev = elem;
294  else
295  pList->*first = pList->*last = elem;
296 
297  (pList->*numElem)++;
298 
299  return iterator(elem);
300  }
301 
303  static inline iterator insertBefore(L* pList, E* elem, E* pNext)
304  {
305  E* pPrev;
306 
307  if (pNext)
308  pPrev = pNext->*prev;
309  else
310  pPrev = 0;
311 
312  elem->*next = pNext;
313  elem->*prev = pPrev;
314 
315  if (pNext)
316  pNext->*prev = elem;
317  else
318  pList->*last = elem;
319  if (pPrev)
320  pPrev->*next = elem;
321  else
322  pList->*first = elem;
323 
324  (pList->*numElem)++;
325  return iterator(elem);
326  }
327 
329  static inline iterator insertBefore(L* pList, E* elem, const iterator& itNext)
330  {
331  return insertBefore(pList, elem, (E*)(*itNext));
332  }
333 
335  static inline iterator insertAfter(L* pList, E* elem, E* pPrev)
336  {
337  E* pNext;
338 
339  if (pPrev)
340  pNext = pPrev->*next;
341  else
342  pNext = 0;
343 
344  elem->*next = pNext;
345  elem->*prev = pPrev;
346 
347  if (pNext)
348  pNext->*prev = elem;
349  else
350  pList->*last = elem;
351  if (pPrev)
352  pPrev->*next = elem;
353  else
354  pList->*first = elem;
355 
356  (pList->*numElem)++;
357  return iterator(elem);
358  }
359 
361  static inline iterator insertAfter(L* pList, E* elem, const iterator& itPrev)
362  {
363  return insertAfter(pList, elem, (E*)(*itPrev));
364  }
365 
367  inline static void popFront(L* pList)
368  {
369  if (front(pList))
370  remove(pList, front(pList));
371  }
372 
374  inline static void popBack(L* pList)
375  {
376  if (back(pList))
377  remove(pList, back(pList));
378  }
379 
381  static inline iterator remove(L* pList, E* elem)
382  {
383  E* pPrev = elem->*prev;
384  E* pNext = elem->*next;
385  if (pPrev)
386  pPrev->*next = pNext;
387  else
388  pList->*first = pNext;
389  if (pNext)
390  pNext->*prev = pPrev;
391  else
392  pList->*last = pPrev;
393 
394  (pList->*numElem)--;
395  return iterator(pNext);
396  }
397 
399  static inline iterator remove(L* pList, const iterator& it)
400  {
401  return remove(pList, (E*)(*it));
402  }
403 
404  template<
405  typename L_other,
406  E* L_other::*other_first,
407  E* L_other::*other_last,
408  int L_other::*other_numElem
409  >
410  inline static void appendFrom( L* pList, L_other* pListOther )
411  {
412  if (!pListOther->*other_first)
413  return;
414 
415  if (empty(pList))
416  {
417  pList->*first = pListOther->*other_first;
418  pList->*last = pListOther->*other_last;
419  } else
420  {
421  // link the pList->last element to other->first
422  pList->*last->*next = pListOther->*other_first;
423  pListOther->*other_first->*prev = pList->*last;
424 
425  // link the pList->last element to other->first
426  pList->*last = pListOther->*other_first;
427  }
428 
429  // add the size of the other pList
430  pList->*numElem += pListOther->*other_numElem;
431  // clear other pList
432  pListOther->*other_numElem = 0;
433  pListOther->*other_first = 0;
434  pListOther->*other_last = 0;
435  }
436 
438  static inline iterator begin(const L* pList) { return iterator(pList->*first); }
439 
441  static inline iterator end(const L* pList) { return iterator(); }
442 
444  static inline iterator rbegin(const L* pList) { return iterator(pList->*last); }
445 
447  static inline iterator rend(const L* pList) { return iterator(); }
448 
449  template<typename Func>
450  static inline void forall(const L* pList, const Func& func)
451  {
452  for(iterator it = begin(pList);it.valid();it++)
453  {
454  func(*it);
455  }
456  }
457 
458  template<typename A1>
459  static inline void forall_call(const L* pList, void (E::*func)( A1 ), const A1& a1)
460  {
461  for(iterator it = begin(pList);it.valid();it++)
462  {
463  ((*it)->*func)(a1);
464  }
465  }
466 
468  inline EList(L* pList) : m_pList(pList) { }
469 
470  inline void init() { init(m_pList); }
471 
472  inline int size() const { return size(m_pList); }
473  inline bool empty() const { return empty(m_pList); }
474 
475  inline E* front() const { return front(m_pList); }
476  inline E* back() const { return back(m_pList); }
477 
478  inline iterator pushBack(E* elem) { return pushBack(m_pList, elem); }
479  inline iterator pushFront(E* elem) { return pushFront(m_pList, elem); }
480 
481  inline iterator insertBefore(E* elem, E* pNext) { return insertBefore(m_pList, elem, pNext); }
482  inline iterator insertBefore(E* elem, const iterator& it) { return insertBefore(m_pList, elem, it); }
483 
484  inline iterator insertAfter(E* elem, E* pPrev) { return insertAfter(m_pList, elem, pPrev); } ;
485  inline iterator insertAfter(E* elem, const iterator& it) { return insertAfter(m_pList, elem, it); } ;
486 
487  inline void popFront() { popFront(m_pList); }
488  inline void popBack() { popBack(m_pList); }
489 
490  void operator<<(E* elem) { pushBack(elem); }
491 
492  inline iterator remove(E* elem) { return remove(m_pList, elem); }
493  inline iterator remove(const iterator& it) { return remove(m_pList, (E*)(*it)); }
494 
495  inline iterator begin() const { return begin(m_pList); }
496  inline iterator end() const { return end(m_pList); }
497  inline iterator rbegin() const { return rbegin(m_pList); }
498  inline iterator rend() const { return rend(m_pList); }
499 
500 private:
502 };
503 
504 
505 } // end of namespace ogdf
506 
507 #endif