Program Listing for File list.hpp¶
↰ Return to documentation for file (libtcod/list.hpp)
/* BSD 3-Clause License
*
* Copyright © 2008-2026, Jice and the libtcod contributors.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its
* contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#pragma once
#ifndef TCOD_LIST_HPP_
#define TCOD_LIST_HPP_
#include <stdlib.h> // NULL
#include <string.h> // memcpy
#include <utility>
#include "list.h"
// fast & lightweight list template
template <class T>
class TCODList {
T* array{};
int fillSize{};
int allocSize{};
public:
[[deprecated("TCODList is unsuitable as a C++ container.")]] TCODList() = default;
TCODList(const TCOD_list_t l) {
for (void** it = TCOD_list_begin(l); it != TCOD_list_end(l); ++it) {
push(*static_cast<T*>(static_cast<void*>(it)));
}
}
TCODList(const TCODList<T>& rhs) { *this = rhs; }
TCODList<T>& operator=(const TCODList<T>& rhs) {
while (allocSize < rhs.allocSize) allocate();
fillSize = rhs.fillSize;
int i = 0;
for (T* t = rhs.begin(); t != rhs.end(); ++t) {
array[i++] = *t;
}
return *this;
}
TCODList(TCODList&& rhs) noexcept { swap(*this, rhs); };
TCODList& operator=(TCODList&& rhs) noexcept {
swap(*this, rhs);
return *this;
}
virtual ~TCODList() {
if (array) delete[] array;
}
friend void swap(TCODList& lhs, TCODList& rhs) noexcept {
using std::swap;
swap(lhs.array, rhs.array);
swap(lhs.fillSize, rhs.fillSize);
swap(lhs.allocSize, rhs.allocSize);
}
[[deprecated("TCODList is unsuitable as a C++ container.")]] TCODList(int nbElements) {
fillSize = 0;
allocSize = nbElements;
array = new T[nbElements];
}
// clang-format off
void set(const T elt, int idx) {
if ( idx < 0 ) return;
while ( allocSize < idx+1 ) allocate();
array[idx] = elt;
if ( idx+1 > fillSize ) fillSize = idx+1;
}
T get(int idx) const {
return array[idx];
}
bool isEmpty() const {
return ( fillSize == 0 );
}
int size() const {
return fillSize;
}
bool contains(const T elt) const
{
for (T* curElt = begin(); curElt != end(); ++curElt) {
if (*curElt == elt) { return true; }
}
return false;
}
T * insertBefore(const T elt,int before) {
if ( fillSize+1 >= allocSize ) allocate();
for (int idx=fillSize; idx > before; idx--) {
array[idx]=array[idx-1];
}
array[before]=elt;
fillSize++;
return &array[before];
}
void remove(const T elt) {
for ( T* curElt = begin(); curElt != end(); curElt ++) {
if ( *curElt == elt ) {
remove(curElt);
return;
}
}
}
void removeFast(const T elt) {
for ( T* curElt = begin(); curElt != end(); curElt ++) {
if ( *curElt == elt ) {
removeFast(curElt);
return;
}
}
}
void addAll(const TCODList<T> &l2) {
for (T *t=l2.begin(); t!= l2.end(); t++) {
push(*t);
}
}
void clear() {
fillSize=0;
}
void clearAndDelete() {
for ( T* curElt = begin(); curElt != end(); curElt ++ ) {
delete (*curElt);
}
fillSize=0;
}
void reverse() {
T* head = begin();
T* tail = end() - 1;
while (head < tail) {
std::swap(*head, *tail);
++head;
--tail;
}
}
void push(const T elt) {
if ( fillSize+1 >= allocSize ) allocate();
array[fillSize++] = elt;
}
T pop() {
if ( fillSize == 0 ) return T{};
return array[--fillSize];
}
T peek() const {
if ( fillSize == 0 ) return T{};
return array[fillSize-1];
}
T * begin() const {
if ( fillSize == 0 ) return (T *)NULL;
return &array[0];
}
T * end() const {
if ( fillSize == 0 ) return (T *)NULL;
return &array[fillSize];
}
T *remove(T *elt) {
for ( T* curElt = elt; curElt < end()-1; curElt ++) {
*curElt = *(curElt+1);
}
fillSize--;
if ( fillSize == 0 ) return ((T *)NULL)-1;
else return elt-1;
}
T *removeFast(T *elt) {
*elt = array[fillSize-1];
fillSize--;
if ( fillSize == 0 ) return ((T *)NULL)-1;
else return elt-1;
}
protected :
void allocate() {
int newSize = allocSize * 2;
if ( newSize == 0 ) newSize = 16;
T *newArray = new T[ newSize ];
if ( array ) {
if ( fillSize > 0 ) memcpy(newArray, array, sizeof(T)*fillSize);
delete [] array;
}
array=newArray;
allocSize=newSize;
}
};
#endif // TCOD_LIST_HPP_