Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00012 #ifndef SMALLSTACK_TYPE_HPP
00013 #define SMALLSTACK_TYPE_HPP
00014
00015 #include "pool_type.hpp"
00016 #include "pool_func.hpp"
00017
00022 template <typename Tindex, typename Titem>
00023 class SmallStackItem {
00024 protected:
00025 Tindex next;
00026 Titem value;
00027
00033 inline SmallStackItem(const Titem &value, Tindex next) :
00034 next(next), value(value) {}
00035 };
00036
00059 template <typename Titem, typename Tindex, Titem Tinvalid, size_t Tgrowth_step, size_t Tmax_size>
00060 class SmallStack : public SmallStackItem<Tindex, Titem> {
00061 protected:
00062 class PooledSmallStack;
00063
00067 void Branch()
00068 {
00069 if (PooledSmallStack::IsValidID(this->next)) {
00070 PooledSmallStack::Get(this->next)->CreateBranch();
00071 }
00072 }
00073
00074 public:
00075 typedef SmallStackItem<Tindex, Titem> Item;
00076 typedef Pool<PooledSmallStack, Tindex, Tgrowth_step, Tmax_size, PT_NORMAL, true, false> SmallStackPool;
00077
00082 inline SmallStack(const Titem &value = Tinvalid) : Item(value, Tmax_size) {}
00083
00087 inline ~SmallStack()
00088 {
00089 if (PooledSmallStack::IsValidID(this->next)) {
00090 PooledSmallStack *item = PooledSmallStack::Get(this->next);
00091 if (item->NumBranches() == 0) {
00092 delete item;
00093 } else {
00094 item->DeleteBranch();
00095 }
00096 }
00097 }
00098
00103 inline SmallStack(const SmallStack &other) : Item(other) { this->Branch(); }
00104
00110 inline SmallStack &operator=(const SmallStack &other)
00111 {
00112 if (this == &other) return *this;
00113 this->~SmallStack();
00114 this->next = other.next;
00115 this->value = other.value;
00116 this->Branch();
00117 return *this;
00118 }
00119
00124 inline void Push(const Titem &item)
00125 {
00126 if (this->value != Tinvalid) {
00127 assert(PooledSmallStack::CanAllocateItem());
00128 PooledSmallStack *next = new PooledSmallStack(this->value, this->next);
00129 this->next = next->index;
00130 }
00131 this->value = item;
00132 }
00133
00138 inline Titem Pop()
00139 {
00140 Titem ret = this->value;
00141 if (!PooledSmallStack::IsValidID(this->next)) {
00142 this->value = Tinvalid;
00143 } else {
00144 PooledSmallStack *next = PooledSmallStack::Get(this->next);
00145 static_cast<Item &>(*this) = *next;
00146 if (next->NumBranches() == 0) {
00147 delete next;
00148 } else {
00149 next->DeleteBranch();
00150 this->Branch();
00151 }
00152 }
00153 return ret;
00154 }
00155
00160 inline bool IsEmpty() const
00161 {
00162 return this->value == Tinvalid && !PooledSmallStack::IsValidID(this->next);
00163 }
00164
00170 inline bool Contains(const Titem &item) const
00171 {
00172 if (item == Tinvalid || item == this->value) return true;
00173 const SmallStack *in_list = this;
00174 while (PooledSmallStack::IsValidID(in_list->next)) {
00175 in_list = static_cast<const SmallStack *>(
00176 static_cast<const Item *>(PooledSmallStack::Get(in_list->next)));
00177 if (in_list->value == item) return true;
00178 }
00179 return false;
00180 }
00181
00182 protected:
00183 static SmallStackPool _pool;
00184
00188 class PooledSmallStack : public Item, public SmallStackPool::template PoolItem<&SmallStack::_pool> {
00189 private:
00190 Tindex branch_count;
00191 public:
00192 PooledSmallStack(Titem value, Tindex next) : Item(value, next), branch_count(0) {}
00193
00194 inline void CreateBranch() { ++this->branch_count; }
00195 inline void DeleteBranch() { --this->branch_count; }
00196 inline Tindex NumBranches() { return this->branch_count; }
00197 };
00198 };
00199
00200
00201 #endif