00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034 #ifndef PTLIB_LISTS_H
00035 #define PTLIB_LISTS_H
00036
00037 #ifdef P_USE_PRAGMA
00038 #pragma interface
00039 #endif
00040
00041
00043
00044
00045 struct PListElement
00046 {
00047 PListElement(PObject * theData);
00048 PListElement * prev;
00049 PListElement * next;
00050 PObject * data;
00051 };
00052
00053 struct PListInfo
00054 {
00055 PListInfo() { head = tail = NULL; }
00056 PListElement * head;
00057 PListElement * tail;
00058 };
00059
00080 class PAbstractList : public PCollection
00081 {
00082 PCONTAINERINFO(PAbstractList, PCollection);
00083
00084 public:
00092 PINLINE PAbstractList();
00094
00095
00123 virtual Comparison Compare(const PObject & obj) const;
00124
00134 virtual PBoolean SetSize(
00135 PINDEX newSize
00136 );
00138
00147 virtual PINDEX Append(
00148 PObject * obj
00149 );
00150
00163 virtual PINDEX Insert(
00164 const PObject & before,
00165 PObject * obj
00166 );
00167
00175 virtual PINDEX InsertAt(
00176 PINDEX index,
00177 PObject * obj
00178 );
00179
00186 virtual PBoolean Remove(
00187 const PObject * obj
00188 );
00189
00199 virtual PObject * RemoveAt(
00200 PINDEX index
00201 );
00202
00214 virtual PBoolean SetAt(
00215 PINDEX index,
00216 PObject * val
00217 );
00218
00229 virtual PBoolean ReplaceAt(
00230 PINDEX index,
00231 PObject * val
00232 );
00233
00244 virtual PObject * GetAt(
00245 PINDEX index
00246 ) const;
00247
00255 virtual PINDEX GetObjectsIndex(
00256 const PObject * obj
00257 ) const;
00258
00267 virtual PINDEX GetValuesIndex(
00268 const PObject & obj
00269 ) const;
00271
00272
00273 protected:
00284 PINLINE PObject & GetReferenceAt(
00285 PINDEX index
00286 ) const;
00287
00297 PBoolean SetCurrent(
00298 PINDEX index,
00299 PListElement * & lastElement
00300 ) const;
00301
00302 PObject * RemoveElement(PListElement * element);
00303
00304
00305 typedef PListElement Element;
00306 PListInfo * info;
00307 };
00308
00309
00316 template <class T> class PList : public PAbstractList
00317 {
00318 PCLASSINFO(PList, PAbstractList);
00319
00320 public:
00328 PList()
00329 : PAbstractList() { }
00331
00337 virtual PObject * Clone() const
00338 { return PNEW PList(0, this); }
00340
00343 class iterator_base : public std::iterator<std::bidirectional_iterator_tag, T> {
00344 protected:
00345 iterator_base(PListElement * e) : element(e) { }
00346 PListElement * element;
00347
00348 void Next() { element = PAssertNULL(element)->next; }
00349 void Prev() { element = PAssertNULL(element)->prev; }
00350 T * Ptr() const { return (T *)PAssertNULL(element)->data; }
00351
00352 public:
00353 bool operator==(const iterator_base & it) const { return element == it.element; }
00354 bool operator!=(const iterator_base & it) const { return element != it.element; }
00355 };
00356
00357 class iterator : public iterator_base {
00358 public:
00359 iterator(PListElement * e = NULL) : iterator_base(e) { }
00360
00361 iterator operator++() { iterator_base::Next(); return *this; }
00362 iterator operator--() { iterator_base::Prev(); return *this; }
00363 iterator operator++(int) { iterator it = *this; iterator_base::Next(); return it; }
00364 iterator operator--(int) { iterator it = *this; iterator_base::Prev(); return it; }
00365
00366 T * operator->() const { return iterator_base::Ptr(); }
00367 T & operator* () const { return *iterator_base::Ptr(); }
00368 };
00369
00370 iterator begin() { return info->head; }
00371 iterator end() { return iterator(); }
00372 iterator rbegin() { return info->tail; }
00373 iterator rend() { return iterator(); }
00374
00375
00376 class const_iterator : public iterator_base {
00377 public:
00378 const_iterator(PListElement * e = NULL) : iterator_base(e) { }
00379
00380 const_iterator operator++() { iterator_base::Next(); return *this; }
00381 const_iterator operator--() { iterator_base::Prev(); return *this; }
00382 const_iterator operator++(int) { const_iterator it = *this; iterator_base::Next(); return it; }
00383 const_iterator operator--(int) { const_iterator it = *this; iterator_base::Prev(); return it; }
00384
00385 const T * operator->() const { return iterator_base::Ptr(); }
00386 const T & operator* () const { return *iterator_base::Ptr(); }
00387 };
00388
00389 const_iterator begin() const { return info->head; }
00390 const_iterator end() const { return const_iterator(); }
00391 const_iterator rbegin() const { return info->tail; }
00392 const_iterator rend() const { return iterator(); }
00393
00394 T & front() const { return *(T *)PAssertNULL(info->head)->data; }
00395 T & back() const { return *(T *)PAssertNULL(info->tail)->data; }
00396 void erase(const iterator & it) { Remove(&*it); }
00397 void erase(const const_iterator & it) { Remove(&*it); }
00398
00399 typedef T value_type;
00401
00415 T & operator[](PINDEX index) const
00416 { return (T &)GetReferenceAt(index); }
00418
00419 protected:
00420 PList(int dummy, const PList * c)
00421 : PAbstractList(dummy, c) { }
00422 };
00423
00424
00436 #define PLIST(cls, T) typedef PList<T> cls
00437
00449 #define PDECLARE_LIST(cls, T) \
00450 PLIST(cls##_PTemplate, T); \
00451 PDECLARE_CLASS(cls, PList<T>) \
00452 protected: \
00453 cls(int dummy, const cls * c) \
00454 : PList<T>(dummy, c) { } \
00455 public: \
00456 cls() \
00457 : PList<T>() { } \
00458 virtual PObject * Clone() const \
00459 { return PNEW cls(0, this); } \
00460
00461
00474 template <class T> class PQueue : public PAbstractList
00475 {
00476 PCLASSINFO(PQueue, PAbstractList);
00477
00478 public:
00487 PQueue()
00488 : PAbstractList() { DisallowDeleteObjects(); }
00490
00496 virtual PObject * Clone() const
00497 { return PNEW PQueue(0, this); }
00499
00505 virtual void Enqueue(
00506 T * obj
00507 ) { PAbstractList::Append(obj); }
00513 virtual T * Dequeue()
00514 { if (GetSize() == 0) return NULL; else return (T *)PAbstractList::RemoveAt(0);}
00516
00517 protected:
00518 PQueue(int dummy, const PQueue * c)
00519 : PAbstractList(dummy, c)
00520 { reference->deleteObjects = c->reference->deleteObjects; }
00521 };
00522
00523
00536 #define PQUEUE(cls, T) typedef PQueue<T> cls
00537
00538
00551 #define PDECLARE_QUEUE(cls, T) \
00552 PQUEUE(cls##_PTemplate, T); \
00553 PDECLARE_CLASS(cls, cls##_PTemplate) \
00554 protected: \
00555 cls(int dummy, const cls * c) \
00556 : cls##_PTemplate(dummy, c) { } \
00557 public: \
00558 cls() \
00559 : cls##_PTemplate() { } \
00560 virtual PObject * Clone() const \
00561 { return PNEW cls(0, this); } \
00562
00563
00576 template <class T> class PStack : public PAbstractList
00577 {
00578 PCLASSINFO(PStack, PAbstractList);
00579
00580 public:
00589 PStack()
00590 : PAbstractList() { DisallowDeleteObjects(); }
00592
00598 virtual PObject * Clone() const
00599 { return PNEW PStack(0, this); }
00601
00608 virtual void Push(
00609 T * obj
00610 ) { PAbstractList::InsertAt(0, obj); }
00611
00617 virtual T * Pop()
00618 { return (T *)PAbstractList::RemoveAt(0); }
00619
00626 virtual T & Top()
00627 { PAssert(GetSize() > 0, PStackEmpty); return *(T *)GetAt(0); }
00629
00630 protected:
00631 PStack(int dummy, const PStack * c)
00632 : PAbstractList(dummy, c)
00633 { reference->deleteObjects = c->reference->deleteObjects; }
00634 };
00635
00636
00649 #define PSTACK(cls, T) typedef PStack<T> cls
00650
00651
00664 #define PDECLARE_STACK(cls, T) \
00665 PSTACK(cls##_PTemplate, T); \
00666 PDECLARE_CLASS(cls, cls##_PTemplate) \
00667 protected: \
00668 cls(int dummy, const cls * c) \
00669 : cls##_PTemplate(dummy, c) { } \
00670 public: \
00671 cls() \
00672 : cls##_PTemplate() { } \
00673 virtual PObject * Clone() const \
00674 { return PNEW cls(0, this); } \
00675
00676
00678
00679
00680 struct PSortedListElement
00681 {
00682 PSortedListElement * parent;
00683 PSortedListElement * left;
00684 PSortedListElement * right;
00685 PObject * data;
00686 PINDEX subTreeSize;
00687 enum { Red, Black } colour;
00688 };
00689
00690 struct PSortedListInfo
00691 {
00692 PSortedListInfo();
00693
00694 PSortedListElement * root;
00695
00696
00697 PSortedListElement nil;
00698
00699 PSortedListElement * Successor(const PSortedListElement * node) const;
00700 PSortedListElement * Predecessor(const PSortedListElement * node) const;
00701 PSortedListElement * OrderSelect(PSortedListElement * node, PINDEX index) const;
00702
00703 typedef PSortedListElement Element;
00704 };
00705
00732 class PAbstractSortedList : public PCollection
00733 {
00734 PCONTAINERINFO(PAbstractSortedList, PCollection);
00735
00736 public:
00744 PAbstractSortedList();
00746
00776 virtual Comparison Compare(const PObject & obj) const;
00778
00788 virtual PBoolean SetSize(
00789 PINDEX newSize
00790 );
00792
00801 virtual PINDEX Append(
00802 PObject * obj
00803 );
00804
00814 virtual PINDEX Insert(
00815 const PObject & before,
00816 PObject * obj
00817 );
00818
00828 virtual PINDEX InsertAt(
00829 PINDEX index,
00830 PObject * obj
00831 );
00832
00843 virtual PBoolean Remove(
00844 const PObject * obj
00845 );
00846
00856 virtual PObject * RemoveAt(
00857 PINDEX index
00858 );
00859
00866 virtual void RemoveAll();
00867
00874 virtual PBoolean SetAt(
00875 PINDEX index,
00876 PObject * val
00877 );
00878
00885 virtual PObject * GetAt(
00886 PINDEX index
00887 ) const;
00888
00900 virtual PINDEX GetObjectsIndex(
00901 const PObject * obj
00902 ) const;
00903 virtual PINDEX GetObjectsIndex(
00904 const PObject * obj,
00905 PSortedListElement * & lastElement
00906 ) const;
00907
00916 virtual PINDEX GetValuesIndex(
00917 const PObject & obj
00918 ) const;
00920
00921
00922 typedef PSortedListElement Element;
00923
00924 protected:
00925
00926
00927 void RemoveElement(Element * node);
00928 void LeftRotate(Element * node);
00929 void RightRotate(Element * node);
00930 void DeleteSubTrees(Element * node, PBoolean deleteObject);
00931 PINDEX ValueSelect(const Element * node, const PObject & obj, const Element ** lastElement) const;
00932
00933
00934 PSortedListInfo * info;
00935 };
00936
00937
00945 template <class T> class PSortedList : public PAbstractSortedList
00946 {
00947 PCLASSINFO(PSortedList, PAbstractSortedList);
00948
00949 public:
00957 PSortedList()
00958 : PAbstractSortedList() { }
00960
00966 virtual PObject * Clone() const
00967 { return PNEW PSortedList(0, this); }
00969
00982 T & operator[](PINDEX index) const
00983 { return *(T *)GetAt(index); }
00985
00986 protected:
00987 PSortedList(int dummy, const PSortedList * c)
00988 : PAbstractSortedList(dummy, c) { }
00989 };
00990
00991
01003 #define PSORTED_LIST(cls, T) typedef PSortedList<T> cls
01004
01005
01018 #define PDECLARE_SORTED_LIST(cls, T) \
01019 PSORTED_LIST(cls##_PTemplate, T); \
01020 PDECLARE_CLASS(cls, PSortedList<T>) \
01021 protected: \
01022 cls(int dummy, const cls * c) \
01023 : PSortedList<T>(dummy, c) { } \
01024 public: \
01025 cls() \
01026 : PSortedList<T>() { } \
01027 virtual PObject * Clone() const \
01028 { return PNEW cls(0, this); } \
01029
01030
01031 #endif // PTLIB_LISTS_H
01032
01033
01034