11#include <util/containers/GStack.h>
27 template <
typename Data>
94 void push(Data& data);
114 Data
const &
peek()
const;
156 template <
typename Data>
168 template <
typename Data>
174 assert(other.capacity_ >= other.size_);
175 if (other.ptrs_ == 0) {
176 assert(other.capacity_ == 0);
177 assert(other.size_ == 0);
182 assert(other.capacity_ > 0);
184 Memory::allocate<Data*>(ptrs_, other.capacity_);
185 capacity_ = other.capacity_;
189 for (
int i = 0; i < size_; ++i) {
190 ptrs_[i] = other.ptrs_[i];
194 if (capacity_ > size_) {
195 for (
int i = size_; i < capacity_; ++i) {
205 template <
typename Data>
218 template <
typename Data>
222 if (
this == &other)
return *
this;
225 for (
int i = 0; i < other.size_; ++i) {
234 template <
typename Data>
238 UTIL_THROW(
"Cannot reserve with capacity <=0");
241 assert(capacity_ == 0);
243 Memory::allocate<Data*>(ptrs_, capacity);
244 capacity_ = capacity;
246 for (
int i = 0; i < capacity_; ++i) {
249 }
else if (capacity > capacity_) {
250 assert(capacity_ > 0);
251 assert(capacity_ >= size_);
254 Memory::allocate<Data*>(newPtr, capacity);
256 for (
int i = 0; i < size_; ++i) {
257 newPtr[i] = ptrs_[i];
260 if (size_ < capacity) {
261 for (
int i = size_; i < capacity; ++i) {
265 Memory::deallocate<Data*>(ptrs_, capacity_);
267 capacity_ = capacity;
274 template <
typename Data>
279 assert(capacity_ > 0);
280 Memory::deallocate<Data*>(ptrs_, capacity_);
288 template <
typename Data>
295 template <
typename Data>
298 if (!isAllocated()) {
299 assert(capacity_ == 0);
300 Memory::allocate<Data*>(ptrs_, 64);
303 for (
int i = 0; i < capacity_; ++i) {
306 }
else if (size_ == capacity_) {
307 assert(capacity_ > 0);
308 assert(capacity_ >= size_);
311 Memory::allocate<Data*>(newPtr, 2*capacity_);
313 for (
int i = 0; i < size_; ++i) {
314 newPtr[i] = ptrs_[i];
317 if (size_ < 2*capacity_) {
318 for (
int i = size_; i < 2*capacity_; ++i) {
322 Memory::deallocate<Data*>(ptrs_, capacity_);
324 capacity_ = 2*capacity_;
329 assert(size_ <= capacity_);
330 ptrs_[size_] = &data;
337 template <
typename Data>
341 UTIL_THROW(
"Attempt to pop from empty stack");
343 Data *ptr = ptrs_[size_-1];
352 template <
typename Data>
354 {
return *ptrs_[size_-1]; }
359 template <
typename Data>
361 {
return *ptrs_[size_-1]; }
366 template <
typename Data>
368 {
return capacity_; }
373 template <
typename Data>
380 template <
class Data>
382 {
return (
bool)ptrs_; }
387 template <
typename Data>
396 if (size_ > capacity_) {
402 for (i = 0; i < size_ ; ++i) {
407 for (i = size_; i < capacity_ ; ++i) {
409 UTIL_THROW(
"Non-null ptrs_[i] for i >= size_");
413 if (capacity_ != 0) {
414 UTIL_THROW(
"Unallocated stack but capacity != 0");
An automatically growable Stack.
bool isAllocated() const
Is this GStack allocated?
GStack< Data > & operator=(GStack< Data > const &other)
Assignment, element by element.
int size() const
Return logical size.
void deallocate()
Deallocate (delete) underlying array of pointers.
int capacity() const
Return allocated size.
Data & peek()
Return a reference to the top element (don't pop).
bool isValid() const
Is this GStack in a valid internal state?
void clear()
Reset to empty state.
void reserve(int capacity)
Reserve memory for specified number of elements.
void push(Data &data)
Push an element onto the stack.
Data & pop()
Pop an element off the stack.
static void deallocate(Data *&ptr, size_t size)
Deallocate a C++ array.
File containing preprocessor macros for error handling.
#define UTIL_THROW(msg)
Macro for throwing an Exception, reporting function, file and line number.
Utility classes for scientific computation.