Add dynamic arrays
This commit is contained in:
@@ -32,10 +32,12 @@ set(BreezeSources
|
|||||||
breeze/core/memory.c
|
breeze/core/memory.c
|
||||||
breeze/core/module_system.c
|
breeze/core/module_system.c
|
||||||
|
|
||||||
breeze/utils/heap.c
|
|
||||||
breeze/map/map.c
|
breeze/map/map.c
|
||||||
breeze/map/tileset.c
|
breeze/map/tileset.c
|
||||||
|
|
||||||
|
breeze/utils/array.c
|
||||||
|
breeze/utils/object_pool.c
|
||||||
|
breeze/utils/heap.c
|
||||||
breeze/utils/tokenizer.c
|
breeze/utils/tokenizer.c
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -48,6 +50,8 @@ set(BreezeHeaders
|
|||||||
breeze/map/map.h
|
breeze/map/map.h
|
||||||
breeze/map/tileset.h
|
breeze/map/tileset.h
|
||||||
|
|
||||||
|
breeze/utils/array.h
|
||||||
|
breeze/utils/object_pool.h
|
||||||
breeze/utils/heap.h
|
breeze/utils/heap.h
|
||||||
breeze/utils/string.h
|
breeze/utils/string.h
|
||||||
breeze/utils/tokenizer.h
|
breeze/utils/tokenizer.h
|
||||||
|
|||||||
@@ -6,6 +6,7 @@
|
|||||||
|
|
||||||
#include "breeze/math/vec2i.h"
|
#include "breeze/math/vec2i.h"
|
||||||
|
|
||||||
|
#include "breeze/utils/array.h"
|
||||||
#include "breeze/utils/heap.h"
|
#include "breeze/utils/heap.h"
|
||||||
#include "breeze/utils/string.h"
|
#include "breeze/utils/string.h"
|
||||||
#include "breeze/utils/tokenizer.h"
|
#include "breeze/utils/tokenizer.h"
|
||||||
|
|||||||
97
engine/breeze/utils/array.c
Normal file
97
engine/breeze/utils/array.c
Normal file
@@ -0,0 +1,97 @@
|
|||||||
|
#include "array.h"
|
||||||
|
|
||||||
|
#include "../core/memory.h"
|
||||||
|
|
||||||
|
typedef struct BzArrayHead {
|
||||||
|
i32 capacity;
|
||||||
|
i32 size;
|
||||||
|
i32 stride;
|
||||||
|
} BzArrayHead;
|
||||||
|
|
||||||
|
#define ARRAY_HEAD(array) (((BzArrayHead *) array) -1)
|
||||||
|
|
||||||
|
void *_bzArrayNew(i32 startCapacity, i32 stride) {
|
||||||
|
BzArrayHead *head = bzAlloc(sizeof(*head) + startCapacity * stride);
|
||||||
|
BZ_ASSERT(startCapacity > 0);
|
||||||
|
head[0] = (BzArrayHead) {
|
||||||
|
.capacity=startCapacity,
|
||||||
|
.size=0,
|
||||||
|
.stride=stride
|
||||||
|
};
|
||||||
|
return &head[1];
|
||||||
|
}
|
||||||
|
void _bzArrayFree(void *arr) {
|
||||||
|
bzFree(ARRAY_HEAD(arr));
|
||||||
|
}
|
||||||
|
void _bzArrayClear(void *arr) {
|
||||||
|
ARRAY_HEAD(arr)->size = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
i32 _bzArraySize(void *arr) {
|
||||||
|
return ARRAY_HEAD(arr)->size;
|
||||||
|
}
|
||||||
|
i32 _bzArrayCapacity(void *arr) {
|
||||||
|
return ARRAY_HEAD(arr)->capacity;
|
||||||
|
}
|
||||||
|
|
||||||
|
void *_bzArrayResize(void **arr, i32 newSize) {
|
||||||
|
BzArrayHead *old = ARRAY_HEAD(*arr);
|
||||||
|
BZ_ASSERT(newSize >= old->size);
|
||||||
|
if (newSize == old->capacity) return *arr;
|
||||||
|
|
||||||
|
BzArrayHead *new = bzResize(old, sizeof(*new) + newSize * old->stride);
|
||||||
|
new[0].capacity = newSize;
|
||||||
|
return &new[1];
|
||||||
|
}
|
||||||
|
void *_bzArrayEnsureCapacity(void **arr, i32 capacity) {
|
||||||
|
BzArrayHead *head = ARRAY_HEAD(*arr);
|
||||||
|
if (capacity > head->capacity)
|
||||||
|
return _bzArrayResize(arr, head->capacity << 1);
|
||||||
|
return *arr;
|
||||||
|
}
|
||||||
|
|
||||||
|
i32 _bzArrayGet(void *arr, i32 idx) {
|
||||||
|
BzArrayHead *head = ARRAY_HEAD(arr);
|
||||||
|
BZ_ASSERT(idx >= 0 && idx < head->size);
|
||||||
|
return idx;
|
||||||
|
}
|
||||||
|
void _bzArrayDelN(void *arr, i32 idx, i32 n) {
|
||||||
|
BzArrayHead *head = ARRAY_HEAD(arr);
|
||||||
|
BZ_ASSERT(n <= head->size);
|
||||||
|
BZ_ASSERT(idx >= 0 && idx + n <= head->size);
|
||||||
|
|
||||||
|
bzMemMove((u8 *) arr + idx * head->stride,
|
||||||
|
(u8 *) arr + (idx + n) * head->stride,
|
||||||
|
n * head->stride);
|
||||||
|
|
||||||
|
head->size -= n;
|
||||||
|
}
|
||||||
|
|
||||||
|
i32 _bzArrayPush(void *arr) {
|
||||||
|
BzArrayHead *head = ARRAY_HEAD(arr);
|
||||||
|
BZ_ASSERT(head->size < head->capacity);
|
||||||
|
i32 insertIdx = head->size;
|
||||||
|
head->size++;
|
||||||
|
return insertIdx;
|
||||||
|
}
|
||||||
|
i32 _bzArrayIns(void *arr, i32 idx) {
|
||||||
|
BzArrayHead *head = ARRAY_HEAD(arr);
|
||||||
|
BZ_ASSERT(idx >= 0 && idx <= head->size);
|
||||||
|
BZ_ASSERT(head->size + 1 <= head->capacity);
|
||||||
|
|
||||||
|
bzMemMove((u8 *) arr + (idx + 1) * head->stride,
|
||||||
|
(u8 *) arr + idx * head->stride, head->stride);
|
||||||
|
head->size++;
|
||||||
|
return idx;
|
||||||
|
}
|
||||||
|
i32 _bzArraySet(void *arr, i32 idx) {
|
||||||
|
BzArrayHead *head = ARRAY_HEAD(arr);
|
||||||
|
BZ_ASSERT(idx >= 0 && idx < head->size);
|
||||||
|
return idx;
|
||||||
|
}
|
||||||
|
i32 _bzArrayPop(void *arr) {
|
||||||
|
BzArrayHead *head = ARRAY_HEAD(arr);
|
||||||
|
BZ_ASSERT(head->size > 0);
|
||||||
|
head->size--;
|
||||||
|
return head->size;
|
||||||
|
}
|
||||||
54
engine/breeze/utils/array.h
Normal file
54
engine/breeze/utils/array.h
Normal file
@@ -0,0 +1,54 @@
|
|||||||
|
#ifndef BREEZE_ARRAY_H
|
||||||
|
#define BREEZE_ARRAY_H
|
||||||
|
|
||||||
|
#include "../defines.h"
|
||||||
|
|
||||||
|
void *_bzArrayNew(i32 startCapacity, i32 stride);
|
||||||
|
void _bzArrayFree(void *arr);
|
||||||
|
void _bzArrayClear(void *arr);
|
||||||
|
|
||||||
|
i32 _bzArraySize(void *arr);
|
||||||
|
i32 _bzArrayCapacity(void *arr);
|
||||||
|
|
||||||
|
void *_bzArrayResize(void **arr, i32 newSize);
|
||||||
|
void *_bzArrayEnsureCapacity(void **arr, i32 capacity);
|
||||||
|
|
||||||
|
i32 _bzArrayGet(void *arr, i32 idx);
|
||||||
|
void _bzArrayDelN(void *arr, i32 idx, i32 n);
|
||||||
|
|
||||||
|
i32 _bzArrayPush(void *arr);
|
||||||
|
i32 _bzArrayIns(void *arr, i32 idx);
|
||||||
|
i32 _bzArraySet(void *arr, i32 idx);
|
||||||
|
i32 _bzArrayPop(void *arr);
|
||||||
|
|
||||||
|
#define bzArrayNew(T, n) (T*) _bzArrayNew(n, sizeof(T))
|
||||||
|
#define bzArrayFree(arr) do { \
|
||||||
|
_bzArrayFree(arr); \
|
||||||
|
arr = NULL; \
|
||||||
|
} while(0)
|
||||||
|
#define bzArrayClear(arr) _bzArrayClear(arr)
|
||||||
|
|
||||||
|
#define bzArraySize(arr) _bzArraySize(arr)
|
||||||
|
#define bzArrayCapacity(arr) _bzArrayCapacity(arr)
|
||||||
|
|
||||||
|
#define bzArrayResize(arr, size) _bzArrayResize((void **) &arr, size)
|
||||||
|
#define bzArrayEnsureCapacity(arr, capacity) _bzArrayEnsureCapacity((void **) &arr, capacity)
|
||||||
|
|
||||||
|
#define bzArrayGet(arr, idx) (arr)[_bzArrayGet(arr, idx)]
|
||||||
|
#define bzArrayDel(arr, idx) _bzArrayDelN(arr, idx, 1)
|
||||||
|
#define bzArrayDelN(arr, idx, n) _bzArrayDelN(arr, idx, n)
|
||||||
|
|
||||||
|
#define bzArrayPush(arr, e) \
|
||||||
|
do { \
|
||||||
|
(arr) = bzArrayEnsureCapacity(arr, bzArraySize(arr) + 1); \
|
||||||
|
(arr)[_bzArrayPush(arr)] = (e); \
|
||||||
|
} while (0)
|
||||||
|
#define bzArrayIns(arr, idx, e) \
|
||||||
|
do { \
|
||||||
|
(arr) = bzArrayEnsureCapacity(arr, bzArraySize(arr) + 1); \
|
||||||
|
(arr)[_bzArrayIns(arr, idx)] = (e); \
|
||||||
|
} while (0)
|
||||||
|
#define bzArraySet(arr, idx, e) (arr)[_bzArraySet(arr, idx)] = e
|
||||||
|
#define bzArrayPop(arr) (arr)[_bzArrayPop(arr)] (arr)[_bzArrayPop(arr)]
|
||||||
|
|
||||||
|
#endif //BREEZE_ARRAY_H
|
||||||
@@ -10,3 +10,6 @@ target_link_libraries(cute_tiled_test LINK_PRIVATE Breeze)
|
|||||||
|
|
||||||
add_executable(heap_test heap_test.c)
|
add_executable(heap_test heap_test.c)
|
||||||
target_link_libraries(heap_test LINK_PRIVATE Breeze)
|
target_link_libraries(heap_test LINK_PRIVATE Breeze)
|
||||||
|
|
||||||
|
add_executable(array_test array_test.c)
|
||||||
|
target_link_libraries(array_test LINK_PRIVATE Breeze)
|
||||||
|
|||||||
52
engine/tests/array_test.c
Normal file
52
engine/tests/array_test.c
Normal file
@@ -0,0 +1,52 @@
|
|||||||
|
#include <breeze.h>
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
int main(void) {
|
||||||
|
bzLoggerInit();
|
||||||
|
int *arr = bzArrayNew(int, 5);
|
||||||
|
|
||||||
|
int i, j;
|
||||||
|
|
||||||
|
BZ_ASSERT(bzArraySize(arr) == 0);
|
||||||
|
for (i = 0; i < 20000; i += 50) {
|
||||||
|
for (j = 0; j < i; ++j)
|
||||||
|
bzArrayPush(arr, j);
|
||||||
|
bzArrayFree(arr);
|
||||||
|
arr = bzArrayNew(int, 5);
|
||||||
|
}
|
||||||
|
|
||||||
|
for (i = 0; i < 4; ++i) {
|
||||||
|
bzArrayPush(arr, 1);
|
||||||
|
bzArrayPush(arr, 2);
|
||||||
|
bzArrayPush(arr, 3);
|
||||||
|
bzArrayPush(arr, 4);
|
||||||
|
bzArrayDel(arr, i);
|
||||||
|
bzArrayFree(arr);
|
||||||
|
arr = bzArrayNew(int, 5);
|
||||||
|
bzArrayPush(arr, 1);
|
||||||
|
bzArrayPush(arr, 2);
|
||||||
|
bzArrayPush(arr, 3);
|
||||||
|
bzArrayPush(arr, 4);
|
||||||
|
//darray_delswap(arr, i);
|
||||||
|
bzArrayFree(arr);
|
||||||
|
arr = bzArrayNew(int, 5);
|
||||||
|
}
|
||||||
|
|
||||||
|
for (i = 0; i < 5; ++i) {
|
||||||
|
bzArrayPush(arr, 1);
|
||||||
|
bzArrayPush(arr, 2);
|
||||||
|
bzArrayPush(arr, 3);
|
||||||
|
bzArrayPush(arr, 4);
|
||||||
|
bzArrayIns(arr, i, 5);
|
||||||
|
BZ_ASSERT(arr[i] == 5);
|
||||||
|
if (i < 4)
|
||||||
|
BZ_ASSERT(arr[4] == 4);
|
||||||
|
bzArrayFree(arr);
|
||||||
|
arr = bzArrayNew(int, 5);
|
||||||
|
}
|
||||||
|
bzArrayFree(arr);
|
||||||
|
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user