colla/darr.h
snarmph 6d36aa4442 .
2025-03-21 19:09:14 +01:00

82 lines
No EOL
2.2 KiB
C

#ifndef COLLA_DARR_HEADER
#define COLLA_DARR_HEADER
/*
dynamic chunked array which uses an arena to allocate,
the structure needs to follow this exact format, if you want
you can use the macro darr_define(struct_name, item_type) instead:
////////////////////////////////////
typedef struct arr_t arr_t;
struct arr_t {
int *items;
usize block_size;
usize count;
arr_t *next;
arr_t *head;
};
// equivalent to
darr_define(arr_t, int);
////////////////////////////////////
by default a chunk is 64 items long, you can change this default
by modifying the arr.block_size value before adding to the array,
or by defining DARRAY_DEFAULT_BLOCK_SIZE
usage example:
////////////////////////////////////
darr_define(arr_t, int);
arr_t *arr = NULL;
for (int i = 0; i < 100; ++i) {
darr_push(&arena, arr, i);
}
for_each (chunk, arr) {
for (int i = 0; i < chunk->count; ++i) {
info("%d -> %d", i, chunk->items[i]);
}
}
*/
#define DARRAY_DEFAULT_BLOCK_SIZE (64)
#define darr_define(struct_name, item_type) typedef struct struct_name struct_name; \
struct struct_name { \
item_type *items; \
usize block_size; \
usize count; \
struct_name *next; \
struct_name *head; \
}
#define darr__alloc_first(arena, arr) do { \
(arr) = (arr) ? (arr) : alloc(arena, typeof(*arr)); \
(arr)->head = (arr)->head ? (arr)->head : (arr); \
(arr)->block_size = (arr)->block_size ? (arr)->block_size : DARRAY_DEFAULT_BLOCK_SIZE; \
(arr)->items = alloc(arena, typeof(*arr->items), arr->block_size); \
assert((arr)->count == 0); \
} while (0)
#define darr__alloc_block(arena, arr) do { \
typeof(arr) newarr = alloc(arena, typeof(*arr)); \
newarr->block_size = arr->block_size; \
newarr->items = alloc(arena, typeof(*arr->items), arr->block_size); \
newarr->head = arr->head; \
arr->next = newarr; \
arr = newarr; \
} while (0)
#define darr_push(arena, arr, item) do { \
if (!(arr) || (arr)->items == NULL) darr__alloc_first(arena, arr); \
if ((arr)->count >= (arr)->block_size) darr__alloc_block(arena, arr); \
(arr)->items[(arr)->count++] = (item); \
} while (0)
#endif