Go to the
documentation of this file.
00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00013 #ifndef _FBXSDK_CORE_BASE_INTRUSIVE_LIST_H_
00014 #define _FBXSDK_CORE_BASE_INTRUSIVE_LIST_H_
00015
00016 #include <fbxsdk/fbxsdk_def.h>
00017
00018 #include <fbxsdk/fbxsdk_nsbegin.h>
00019
00020
00021
00022
00023 #ifndef DOXYGEN_SHOULD_SKIP_THIS
00024
00025 #define FBXSDK_INTRUSIVE_LIST_NODE(Class, NodeCount)\
00026 public: inline FbxListNode<Class>& GetListNode(int index = 0){ return this->mNode[index]; }\
00027 private: FbxListNode<Class> mNode[NodeCount];
00028
00029 template <typename T> class FbxListNode
00030 {
00031 typedef FbxListNode<T> NodeT;
00032
00033 public:
00034 explicit FbxListNode(T* pData = 0):mNext(0),mPrev(0),mData(pData){}
00035 ~FbxListNode(){ Disconnect(); }
00036
00037 void Disconnect()
00038 {
00039 if ( mPrev != 0 )
00040 mPrev->mNext = mNext;
00041
00042 if ( mNext != 0 )
00043 mNext->mPrev = mPrev;
00044
00045 mPrev = mNext = 0;
00046 }
00047
00048 NodeT* mNext;
00049 NodeT* mPrev;
00050 T* mData;
00051 };
00052
00053
00054
00055
00056
00057 template <typename T, int NodeIndex=0> class FbxIntrusiveList
00058 {
00059 public:
00060 typedef T allocator_type;
00061 typedef T value_type;
00062 typedef T& reference;
00063 typedef const T& const_reference;
00064 typedef T* pointer;
00065 typedef const T* const_pointer;
00066
00067 typedef FbxListNode<T> NodeT;
00068
00069
00070 FbxIntrusiveList():mHead(0)
00071 {
00072 mHead.mNext = mHead.mPrev = &mHead;
00073 }
00074 ~FbxIntrusiveList()
00075 {
00076 while(!Empty())
00077 Begin().Get()->Disconnect();
00078 };
00079
00080
00081 bool Empty() const
00082 {
00083 return ((mHead.mNext==&mHead)&&(mHead.mPrev==&mHead));
00084 }
00085
00086
00087 void PushBack(T& pElement)
00088 {
00089 NodeT* pNode = &pElement.GetListNode(NodeIndex);
00090 pNode->mData = &pElement;
00091
00092 if (Empty())
00093 {
00094 pNode->mNext = &mHead;
00095 pNode->mPrev = &mHead;
00096 mHead.mNext = pNode;
00097 mHead.mPrev = pNode;
00098 }
00099 else
00100 {
00101 pNode->mNext = &mHead;
00102 pNode->mPrev = mHead.mPrev;
00103
00104 pNode->mPrev->mNext = pNode;
00105 mHead.mPrev = pNode;
00106 }
00107 }
00108
00109 void PushFront(T& pElement)
00110 {
00111 NodeT* pNode = &pElement.GetListNode(NodeIndex);
00112 pNode->mData = &pElement;
00113
00114 if (Empty())
00115 {
00116 pNode->mNext = &mHead;
00117 pNode->mPrev = &mHead;
00118 mHead.mNext = pNode;
00119 mHead.mPrev = pNode;
00120 }
00121 else
00122 {
00123 pNode->mNext = mHead.mNext;
00124 pNode->mPrev = &mHead;
00125
00126 pNode->mNext->mPrev = pNode;
00127 mHead.mNext = pNode;
00128 }
00129 }
00130
00131 void PopFront()
00132 {
00133 iterator begin = Begin();
00134 Erase(begin);
00135 }
00136
00137 void PopBack()
00138 {
00139 Erase(--(End()));
00140 }
00141
00142 public:
00143 class IntrusiveListIterator
00144 {
00145 public:
00146 explicit IntrusiveListIterator(NodeT* ptr=0):mPtr(ptr){}
00147
00148
00149 IntrusiveListIterator& operator++()
00150 {
00151 mPtr = mPtr->mNext;return (*this);
00152 }
00153
00154 const IntrusiveListIterator operator++(int)
00155 {
00156 IntrusiveListIterator temp = *this;
00157 ++*this;
00158 return (temp);
00159 }
00160
00161 IntrusiveListIterator& operator--()
00162 {
00163 mPtr = mPtr->mPrev;return *this;
00164 }
00165
00166 const IntrusiveListIterator operator--(int)
00167 {
00168 IntrusiveListIterator temp = *this;
00169 --*this;
00170 return (temp);
00171 }
00172 IntrusiveListIterator& operator=(const IntrusiveListIterator &other){mPtr = other.mPtr; return *this;}
00173
00174 reference operator*() const { return *(mPtr->mData); }
00175 pointer operator->() const { return (&**this); }
00176 bool operator==(const IntrusiveListIterator& other)const{ return mPtr==other.mPtr; }
00177 bool operator!=(const IntrusiveListIterator& other)const{ return !(*this == other); }
00178
00179 inline NodeT* Get()const { return mPtr; }
00180
00181 private:
00182 NodeT* mPtr;
00183 };
00184
00185 class IntrusiveListConstIterator
00186 {
00187 public:
00188 explicit IntrusiveListConstIterator(const NodeT* ptr=0):mPtr(ptr){}
00189
00190
00191 IntrusiveListConstIterator& operator++()
00192 {
00193 mPtr = mPtr->mNext;return (*this);
00194 }
00195
00196 const IntrusiveListConstIterator operator++(int)
00197 {
00198 IntrusiveListConstIterator temp = *this;
00199 ++*this;
00200 return (temp);
00201 }
00202
00203 IntrusiveListConstIterator& operator--()
00204 {
00205 mPtr = mPtr->mPrev;return *this;
00206 }
00207
00208 const IntrusiveListConstIterator operator--(int)
00209 {
00210 IntrusiveListConstIterator temp = *this;
00211 --*this;
00212 return (temp);
00213 }
00214 IntrusiveListConstIterator& operator=(const IntrusiveListConstIterator &other){mPtr = other.mPtr; return *this;}
00215
00216 const_reference operator*() const { return *(mPtr->mData); }
00217 const_pointer operator->() const { return (&**this); }
00218 bool operator==(const IntrusiveListConstIterator& other)const{ return mPtr==other.mPtr; }
00219 bool operator!=(const IntrusiveListConstIterator& other)const{ return !(*this == other); }
00220
00221 inline const NodeT* Get()const { return mPtr; }
00222
00223 private:
00224 mutable const NodeT* mPtr;
00225 };
00226
00227
00228 typedef IntrusiveListIterator iterator;
00229 typedef IntrusiveListConstIterator const_iterator;
00230
00231
00232 inline iterator Begin() { return iterator(mHead.mNext); }
00233 inline const_iterator Begin() const { return const_iterator(mHead.mNext); }
00234 inline iterator End() { return iterator(&mHead); }
00235 inline const_iterator End() const { return const_iterator(&mHead); }
00236
00237
00238
00239
00240 reference Front(){return (*Begin());}
00241 const_reference Front() const { return (*Begin()); }
00242 reference Back(){ return (*(--End())); }
00243 const_reference Back() const{ return (*(--End())); }
00244
00245 iterator& Erase(iterator& it)
00246 {
00247 it.Get()->Disconnect();
00248 return (++it);
00249 }
00250 private:
00251 NodeT mHead;
00252
00253
00254 FbxIntrusiveList(const FbxIntrusiveList&);
00255 FbxIntrusiveList& operator=(const FbxIntrusiveList& Right){return (*this);}
00256 };
00257
00258 #endif
00259
00260 #include <fbxsdk/fbxsdk_nsend.h>
00261
00262 #endif