Browse Source

First commit

master
Kenneth Bruen 3 years ago
commit
5789f53721
Signed by: kbruen
GPG Key ID: C1980A470C3EE5B1
  1. 2
      .gitignore
  2. 22
      Makefile
  3. 29
      README.md
  4. 160
      dynarray.hpp
  5. 38
      example.cpp

2
.gitignore vendored

@ -0,0 +1,2 @@
obj
example

22
Makefile

@ -0,0 +1,22 @@
CXX?=g++
.PHONY: debug run clean
example: obj/example.o
${CXX} $^ -o $@
run: example
./example
debug:
COMPILE_FLAGS="-D DEBUG" make -B example
obj:
@if [ ! -d obj ]; then mkdir obj; fi
obj/%.o: %.cpp | obj
${CXX} ${COMPILE_FLAGS} -c $^ -o $@
clean:
@if [ -d obj ]; then echo rm -r obj; rm -r obj; fi
@if [ -f example ]; then echo rm example; rm example; fi

29
README.md

@ -0,0 +1,29 @@
# DynArray: basic dynamic array (list/vector) implementation
Why? Why not.
## How to run?
### Got make?
```shell
make run
```
### No make?
```shell
g++ example.cpp -o example
./example
```
### Windows?
```powershell
g++ example.cpp -o example.exe
.\example.exe
```
### Windows without `g++`?
I never compiled something using `msvc` from the terminal. I guess make a new Visual Studio project, copy-paste the files in there and have fun, idk.

160
dynarray.hpp

@ -0,0 +1,160 @@
#pragma once
#ifdef DEBUG
#define TMP_DEBUG_12345 DEBUG
#undef DEBUG
#include <iostream>
using std::cerr;
#define DEBUG (cerr << "[DynArray " << this << "] ")
#endif
template <class T>
class DynArray {
private:
T* _buffer;
size_t _length;
size_t _capacity;
public:
explicit DynArray(size_t capacity = 64)
: _buffer(new T[capacity])
, _length(0)
, _capacity(capacity) {
#ifdef DEBUG
DEBUG << "New array with capacity " << capacity << '\n';
#endif
}
~DynArray() {
#ifdef DEBUG
DEBUG << "Destroyed" << '\n';
#endif
delete[] _buffer;
}
size_t size() const {
return _length;
}
size_t length() const {
return _length;
}
operator bool() const {
return length() > 0;
}
size_t capacity() const {
return _capacity;
}
void push_back(T element) {
if (_length + 1 > _capacity) {
#ifdef DEBUG
DEBUG << "Push attempt when length and capacity are " << _capacity << ", reallocating" << '\n';
#endif
T *new_buffer = new T[_capacity * 2];
for (size_t i = 0; i < _capacity; ++i) {
new_buffer[i] = _buffer[i];
}
delete[] _buffer;
_buffer = new_buffer;
_capacity *= 2;
}
_buffer[_length++] = element;
}
DynArray<T>& operator<<(T element) {
push_back(element);
return *this;
}
void pop_back() {
_length--;
}
T& operator[](size_t index) {
return _buffer[index];
}
const T& operator[](size_t index) const {
return _buffer[index];
}
// Iterator bullshit
class iterator {
private:
DynArray<T>* _arr;
size_t _index;
public:
// Default constructible
iterator() : _arr(nullptr), _index(-1) {}
iterator(DynArray<T> &arr, size_t index = 0) : _arr(&arr), _index(index) {}
// Copy constructible
iterator(const iterator &it) : _arr(it._arr), _index(it._index) {}
// Copy assignable
iterator& operator=(const iterator& it) {
_arr = it._arr;
_index = it._index;
}
// Comparable
bool operator==(const iterator& it) const {
return _arr == it._arr && _index == it._index;
}
bool operator!=(const iterator& it) const {
return !(*this == it);
}
// Dereferencable
T& operator*() {
return (*_arr)[_index];
}
const T& operator*() const {
return (*_arr)[_index];
}
T* operator->() {
return &((*_arr)[_index]);
}
const T* operator->() const {
return &((*_arr)[_index]);
}
// Can be incremented
iterator& operator++() {
_index++;
return *this;
}
iterator operator++(int) {
auto copy = *this;
++*this;
return copy;
}
};
iterator begin() {
return iterator(*this);
}
const iterator begin() const {
return iterator(*this);
}
iterator end() {
return iterator(*this, size());
}
const iterator end() const {
return iterator(*this, size());
}
};
#ifdef TMP_DEBUG_12345
#ifdef DEBUG
#undef DEBUG
#endif
#define DEBUG TMP_DEBUG_12345
#undef TMP_DEBUG_12345
#endif

38
example.cpp

@ -0,0 +1,38 @@
#include <iostream>
#include <random>
using std::cout;
using std::cin;
#include "dynarray.hpp"
int main() {
size_t n;
cout << "How many numbers to generate? ";
cin >> n;
std::default_random_engine r_eng;
DynArray<std::default_random_engine::result_type> arr;
for (auto i = 0; i < n; i++)
{
arr << r_eng();
}
cout << '\n';
cout << "Size: " << arr.size() << '\n';
cout << "Capacity: " << arr.capacity() << '\n';
cout << "Elements: [";
bool first = true;
for (auto elem : arr)
{
if (!first) {
cout << ", ";
}
else {
first = false;
}
cout << elem;
}
cout << "]\n";
return 0;
}
Loading…
Cancel
Save