123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751 |
- ////////////////////////////////////////////////////////////////////////////////////////
- // RAVEN STANDARD TEMPLATE LIBRARY
- // (c) 2002 Activision
- //
- //
- // List
- // ----
- // The list class supports ordered insertion and deletion in O(1) constant time.
- // It simulates a linked list of pointers by allocating free spots in a pool and
- // maintaining "links" as indicies to the pool array objects.
- //
- //
- //
- // NOTES:
- //
- //
- //
- ////////////////////////////////////////////////////////////////////////////////////////
- #if !defined(RATL_LIST_VS_INC)
- #define RATL_LIST_VS_INC
- ////////////////////////////////////////////////////////////////////////////////////////
- // Includes
- ////////////////////////////////////////////////////////////////////////////////////////
- #if defined(RA_DEBUG_LINKING)
- #pragma message("...including list_vs.h")
- #endif
- #if !defined(RATL_COMMON_INC)
- #include "ratl_common.h"
- #endif
- #if !defined(RATL_POOL_VS_INC)
- #include "pool_vs.h"
- #endif
- namespace ratl
- {
- // this is private to the list, but you have no access to it, soooo..
- class list_node
- {
- public:
- int mNext;
- int mPrev;
- };
- ////////////////////////////////////////////////////////////////////////////////////////
- // The List Class
- ////////////////////////////////////////////////////////////////////////////////////////
- template <class T>
- class list_base : public ratl_base
- {
- public:
- typedef typename T TStorageTraits;
- typedef typename T::TValue TTValue;
- ////////////////////////////////////////////////////////////////////////////////////
- // Capacity Enum
- ////////////////////////////////////////////////////////////////////////////////////
- enum
- {
- CAPACITY = T::CAPACITY
- };
- private:
- ////////////////////////////////////////////////////////////////////////////////////
- // Data
- ////////////////////////////////////////////////////////////////////////////////////
- pool_base<TStorageTraits> mPool; // The Allocation Data Pool
- int mFront; // The Beginning Of The List
- int mBack; // The End Of The List
- enum
- {
- NULL_NODE = -1
- };
- public:
- ////////////////////////////////////////////////////////////////////////////////////
- // Constructor
- ////////////////////////////////////////////////////////////////////////////////////
- list_base() : mFront(NULL_NODE), mBack(NULL_NODE)
- {
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // How Many Objects Are In This List
- ////////////////////////////////////////////////////////////////////////////////////
- int size() const
- {
- return (mPool.size());
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Are There Any Objects In This List?
- ////////////////////////////////////////////////////////////////////////////////////
- bool empty() const
- {
- assert(mFront!=NULL_NODE || size()==0);
- return (mFront==NULL_NODE);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Is This List Filled?
- ////////////////////////////////////////////////////////////////////////////////////
- bool full() const
- {
- return (mPool.full());
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Clear All Elements
- ////////////////////////////////////////////////////////////////////////////////////
- void clear()
- {
- mFront = NULL_NODE;
- mBack = NULL_NODE;
- mPool.clear();
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Get The First Object In The List
- ////////////////////////////////////////////////////////////////////////////////////
- TTValue & front()
- {
- assert(mFront!=NULL_NODE); // this is empty
- return mPool[mFront];
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Get The Last Object In The List
- ////////////////////////////////////////////////////////////////////////////////////
- TTValue & back()
- {
- assert(mBack!=NULL_NODE);
- return mPool[mBack];
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Get The First Object In The List
- ////////////////////////////////////////////////////////////////////////////////////
- const TTValue & front() const
- {
- assert(mFront!=NULL_NODE); // this is empty
- return mPool[mFront];
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Get The Last Object In The List
- ////////////////////////////////////////////////////////////////////////////////////
- const TTValue & back() const
- {
- assert(mBack!=NULL_NODE);
- return mPool[mBack];
- }
- public:
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator
- ////////////////////////////////////////////////////////////////////////////////////
- class const_iterator;
- class iterator
- {
- friend class list_base<T>;
- friend class const_iterator;
- int mLoc;
- list_base<T>* mOwner;
- public:
- // Constructors
- //--------------
- iterator() : mOwner(0), mLoc(0)
- {}
- iterator(list_base* p, int t) : mOwner(p), mLoc(t)
- {}
- iterator(const iterator &t) : mOwner(t.mOwner), mLoc(t.mLoc)
- {}
- // Assignment Operator
- //---------------------
- void operator= (const iterator &t)
- {
- mOwner = t.mOwner;
- mLoc = t.mLoc;
- }
- // Equality Operators
- //--------------------
- bool operator!=(const iterator &t) const
- {
- return (mLoc!=t.mLoc || mOwner!=t.mOwner);
- }
- bool operator==(const iterator &t) const
- {
- return (mLoc==t.mLoc && mOwner==t.mOwner);
- }
- // DeReference Operator
- //----------------------
- TTValue& operator* () const
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- return (mOwner->mPool[mLoc]);
- }
- // DeReference Operator
- //----------------------
- TTValue& value() const
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- return (mOwner->mPool[mLoc]);
- }
- // DeReference Operator
- //----------------------
- TTValue* operator-> () const
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- return (&mOwner->mPool[mLoc]);
- }
- // prefix Inc Operator
- //--------------
- iterator operator++(int)
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- iterator old(*this);
- mLoc = T::node(mOwner->mPool[mLoc]).mNext;
- return old;
- }
- // postfix Inc Operator
- //--------------
- iterator operator++()
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- mLoc = T::node(mOwner->mPool[mLoc]).mNext;
- return *this;
- }
- // prefix Inc Operator
- //--------------
- iterator operator--(int)
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- iterator old(*this);
- mLoc = T::node(mOwner->mPool[mLoc]).mPrev;
- return old;
- }
- //--------------
- // postfix Dec Operator
- //--------------
- iterator operator--()
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- mLoc = T::node(mOwner->mPool[mLoc]).mPrev;
- return *this;
- }
- };
- ////////////////////////////////////////////////////////////////////////////////////
- // Constant Iterator
- ////////////////////////////////////////////////////////////////////////////////////
- class const_iterator
- {
- friend class list_base<T>;
- int mLoc;
- const list_base<T>* mOwner;
- public:
- // Constructors
- //--------------
- const_iterator() : mOwner(0), mLoc(0)
- {}
- const_iterator(const list_base* p, int t) : mOwner(p), mLoc(t)
- {}
- const_iterator(const const_iterator &t) : mOwner(t.mOwner), mLoc(t.mLoc)
- {}
- const_iterator(const iterator &t) : mOwner(t.mOwner), mLoc(t.mLoc)
- {}
- // Assignment Operator
- //---------------------
- void operator= (const const_iterator &t)
- {
- mOwner = t.mOwner;
- mLoc = t.mLoc;
- }
- // Assignment Operator
- //---------------------
- void operator= (const iterator &t)
- {
- mOwner = t.mOwner;
- mLoc = t.mLoc;
- }
- // Equality Operators
- //--------------------
- bool operator!=(const iterator &t) const
- {
- return (mLoc!=t.mLoc || mOwner!=t.mOwner);
- }
- bool operator==(const iterator &t) const
- {
- return (mLoc==t.mLoc && mOwner==t.mOwner);
- }
- // Equality Operators
- //--------------------
- bool operator!=(const const_iterator &t) const
- {
- return (mLoc!=t.mLoc || mOwner!=t.mOwner);
- }
- bool operator==(const const_iterator &t) const
- {
- return (mLoc==t.mLoc && mOwner==t.mOwner);
- }
- // DeReference Operator
- //----------------------
- const TTValue& operator* () const
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- return (mOwner->mPool[mLoc]);
- }
- // DeReference Operator
- //----------------------
- const TTValue* operator-> () const
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- return (&mOwner->mPool[mLoc]);
- }
- // DeReference Operator
- //----------------------
- const TTValue& value() const
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- return (mOwner->mPool[mLoc]);
- }
- // prefix Inc Operator
- //--------------
- const_iterator operator++(int)
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- const_iterator old(*this);
- mLoc = T::node(mOwner->mPool[mLoc]).mNext;
- return old;
- }
- // postfix Inc Operator
- //--------------
- const_iterator operator++()
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- mLoc = T::node(mOwner->mPool[mLoc]).mNext;
- return *this;
- }
- // prefix Inc Operator
- //--------------
- const_iterator operator--(int)
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- const_iterator old(*this);
- mLoc = T::node(mOwner->mPool[mLoc]).mPrev;
- return old;
- }
- //--------------
- // postfix Dec Operator
- //--------------
- const_iterator operator--()
- {
- assert(mLoc>=0 && mLoc<T::CAPACITY);
- mLoc = T::node(mOwner->mPool[mLoc]).mPrev;
- return *this;
- }
- };
- friend class iterator;
- friend class const_iterator;
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Begin (Starts At Address mFront)
- ////////////////////////////////////////////////////////////////////////////////////
- iterator begin()
- {
- return iterator(this, mFront);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Begin (Starts At Address mFront)
- ////////////////////////////////////////////////////////////////////////////////////
- const_iterator begin() const
- {
- return const_iterator(this, mFront);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Reverse Iterator Begin (Starts At Address mBack)
- ////////////////////////////////////////////////////////////////////////////////////
- iterator rbegin()
- {
- return iterator(this, mBack);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Reverse Iterator Begin (Starts At Address mBack)
- ////////////////////////////////////////////////////////////////////////////////////
- const_iterator rbegin() const
- {
- return const_iterator(this, mBack);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator End (Set To Address NULL_NODE) Should Work For Forward & Backward Iteration
- ////////////////////////////////////////////////////////////////////////////////////
- iterator end()
- {
- return iterator(this, NULL_NODE);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator End (Set To Address NULL_NODE) Should Work For Forward & Backward Iteration
- ////////////////////////////////////////////////////////////////////////////////////
- const_iterator end() const
- {
- return const_iterator(this, NULL_NODE);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Insert (BEFORE POINTED ELEMENT)
- ////////////////////////////////////////////////////////////////////////////////////
- T& insert(const iterator& it)
- {
- int nNew= mPool.alloc();
- insert_low(it,nNew);
- return mPool[mNew];
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Insert Value(BEFORE POINTED ELEMENT)
- ////////////////////////////////////////////////////////////////////////////////////
- void insert(const iterator& it, const TTValue& val)
- {
- int nNew= mPool.alloc(val);
- insert_low(it,nNew);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Insert Raw(BEFORE POINTED ELEMENT)
- ////////////////////////////////////////////////////////////////////////////////////
- TRatlNew* insert_raw(const iterator& it)
- {
- TRatlNew *ret = mPool.alloc_raw();
- insert_low(it,mPool.pointer_to_index(ret));
- return ret;
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Insert (AFTER POINTED ELEMENT) (ALSO - NOT CONSTANT, WILL CHANGE it)
- ////////////////////////////////////////////////////////////////////////////////////
- T& insert_after(iterator& it)
- {
- int nNew= mPool.alloc();
- insert_low_after(it,nNew);
- it = iterator(this, nNew);
- return mPool[mNew];
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Insert Value(AFTER POINTED ELEMENT) (ALSO - NOT CONSTANT, WILL CHANGE it)
- ////////////////////////////////////////////////////////////////////////////////////
- void insert_after(iterator& it, const TTValue& val)
- {
- int nNew= mPool.alloc(val);
- insert_low_after(it,nNew);
- it = iterator(this, nNew);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Insert Raw(AFTER POINTED ELEMENT) (ALSO - NOT CONSTANT, WILL CHANGE it)
- ////////////////////////////////////////////////////////////////////////////////////
- TRatlNew* insert_raw_after(iterator& it)
- {
- TRatlNew *ret = mPool.alloc_raw();
- insert_low_after(it,mPool.pointer_to_index(ret));
- it = iterator(this, mPool.pointer_to_index(ret));
- return ret;
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Front Insert (BEFORE POINTED ELEMENT)
- ////////////////////////////////////////////////////////////////////////////////////
- T& push_front()
- {
- int nNew= mPool.alloc();
- insert_low(begin(),nNew);
- return mPool[mNew];
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Front Insert Value(BEFORE POINTED ELEMENT)
- ////////////////////////////////////////////////////////////////////////////////////
- void push_front(const TTValue& val)
- {
- int nNew= mPool.alloc(val);
- insert_low(begin(),nNew);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Front Insert Raw(BEFORE POINTED ELEMENT)
- ////////////////////////////////////////////////////////////////////////////////////
- TRatlNew * push_front_raw()
- {
- TRatlNew *ret = mPool.alloc_raw();
- insert_low(begin(),mPool.pointer_to_index(ret));
- return ret;
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Front Insert (BEFORE POINTED ELEMENT)
- ////////////////////////////////////////////////////////////////////////////////////
- T& push_back()
- {
- int nNew= mPool.alloc();
- insert_low(end(),nNew);
- return mPool[mNew];
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Front Insert Value(BEFORE POINTED ELEMENT)
- ////////////////////////////////////////////////////////////////////////////////////
- void push_back(const TTValue& val)
- {
- int nNew= mPool.alloc(val);
- insert_low(end(),nNew);
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Front Insert Raw(BEFORE POINTED ELEMENT)
- ////////////////////////////////////////////////////////////////////////////////////
- TRatlNew * push_back_raw()
- {
- TRatlNew *ret = mPool.alloc_raw();
- insert_low(end(),mPool.pointer_to_index(ret));
- return ret;
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Erase
- ////////////////////////////////////////////////////////////////////////////////////
- void erase(iterator& it)
- {
- assert(it.mOwner==this); // Iterators must be mixed up, this is from a different list.
- assert(it.mLoc!=NULL_NODE);
- int At = it.mLoc;
- int Prev = T::node(mPool[At]).mPrev;
- int Next = T::node(mPool[At]).mNext;
- // LINK: (Prev)<-(At)--(Next)
- //--------------------------------------------
- if (Next!=NULL_NODE)
- {
- T::node(mPool[Next]).mPrev = Prev;
- }
- // LINK: (Prev)--(At)->(Next)
- //--------------------------------------------
- if (Prev!=NULL_NODE)
- {
- T::node(mPool[Prev]).mNext = Next;
- }
- // UPDATE: Front & Back
- //----------------------
- if (At==mBack)
- {
- mBack = Prev;
- }
- if (At==mFront)
- {
- mFront = Next;
- }
- // ERASE At
- //--------------------------------------------
- mPool.free(At);
- it.mLoc = Prev;
- }
- template<class CAST_TO>
- CAST_TO *verify_alloc(CAST_TO *p) const
- {
- return mPool.verify_alloc(p);
- }
- private:
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Insert, returns pool index
- ////////////////////////////////////////////////////////////////////////////////////
- void insert_low(const iterator& it,int nNew)
- {
- assert(it.mOwner==this); // Iterators must be mixed up, this is from a different list.
- int Next = it.mLoc;
- int Prev = NULL_NODE;
- if (Next!=NULL_NODE)
- {
- Prev = T::node(mPool[Next]).mPrev;
- }
- else
- {
- Prev = mBack;
- }
- assert(nNew!=Next && nNew!=Prev);
- // LINK: (Prev)<-(New)->(Next)
- //--------------------------------------------
- T::node(mPool[nNew]).mPrev = Prev;
- T::node(mPool[nNew]).mNext = Next;
- // LINK: (New)<-(Next)
- //--------------------------------------------
- if (Next!=NULL_NODE)
- {
- T::node(mPool[Next]).mPrev = nNew;
- assert(T::node(mPool[Next]).mPrev!=T::node(mPool[Next]).mNext);
- }
- else
- {
- mBack = nNew;
- }
- // LINK: (Prev)->(New)
- //--------------------------------------------
- if (Prev!=NULL_NODE)
- {
- T::node(mPool[Prev]).mNext = nNew;
- assert(T::node(mPool[Prev]).mPrev!=T::node(mPool[Prev]).mNext);
- }
- else
- {
- mFront = nNew;
- }
- }
- ////////////////////////////////////////////////////////////////////////////////////
- // Iterator Insert, returns pool index (AFTER POINTED ELEMENT)
- ////////////////////////////////////////////////////////////////////////////////////
- void insert_low_after(const iterator& it,int nNew)
- {
- assert(it.mOwner==this); // Iterators must be mixed up, this is from a different list.
- int Next = NULL_NODE;//it.mLoc;
- int Prev = it.mLoc;//NULL_NODE;
- if (Prev!=NULL_NODE)
- {
- Next = T::node(mPool[Prev]).mNext;
- }
- else
- {
- Prev = mFront;
- }
- assert(nNew!=Next && nNew!=Prev);
- // LINK: (Prev)<-(New)->(Next)
- //--------------------------------------------
- T::node(mPool[nNew]).mPrev = Prev;
- T::node(mPool[nNew]).mNext = Next;
- // LINK: (New)<-(Next)
- //--------------------------------------------
- if (Next!=NULL_NODE)
- {
- T::node(mPool[Next]).mPrev = nNew;
- assert(T::node(mPool[Next]).mPrev!=T::node(mPool[Next]).mNext);
- }
- else
- {
- mBack = nNew;
- }
- // LINK: (Prev)->(New)
- //--------------------------------------------
- if (Prev!=NULL_NODE)
- {
- T::node(mPool[Prev]).mNext = nNew;
- assert(T::node(mPool[Prev]).mPrev!=T::node(mPool[Prev]).mNext);
- }
- else
- {
- mFront = nNew;
- }
- }
- };
- template<class T, int ARG_CAPACITY>
- class list_vs : public list_base<storage::value_semantics_node<T,ARG_CAPACITY,list_node> >
- {
- public:
- typedef typename storage::value_semantics_node<T,ARG_CAPACITY,list_node> TStorageTraits;
- typedef typename TStorageTraits::TValue TTValue;
- enum
- {
- CAPACITY = ARG_CAPACITY
- };
- list_vs() {}
- };
- template<class T, int ARG_CAPACITY>
- class list_os : public list_base<storage::object_semantics_node<T,ARG_CAPACITY,list_node> >
- {
- public:
- typedef typename storage::object_semantics_node<T,ARG_CAPACITY,list_node> TStorageTraits;
- typedef typename TStorageTraits::TValue TTValue;
- enum
- {
- CAPACITY = ARG_CAPACITY
- };
- list_os() {}
- };
- template<class T, int ARG_CAPACITY, int ARG_MAX_CLASS_SIZE>
- class list_is : public list_base<storage::virtual_semantics_node<T,ARG_CAPACITY,ARG_MAX_CLASS_SIZE,list_node> >
- {
- public:
- typedef typename storage::virtual_semantics_node<T,ARG_CAPACITY,ARG_MAX_CLASS_SIZE,list_node> TStorageTraits;
- typedef typename TStorageTraits::TValue TTValue;
- enum
- {
- CAPACITY = ARG_CAPACITY,
- MAX_CLASS_SIZE = ARG_MAX_CLASS_SIZE
- };
- list_is() {}
- };
- }
- #endif
|