aboutsummaryrefslogtreecommitdiff
path: root/src/ivec.c
diff options
context:
space:
mode:
authorElis Eriksson <spelis@spelis.li>2026-06-13 17:40:25 +0200
committerElis Eriksson <spelis@spelis.li>2026-06-13 17:40:25 +0200
commit7ccae1c362a45b28f4fbf96da4f479730e4b382b (patch)
treef59ba4d76221590901784464a03a6a871d774305 /src/ivec.c
downloadbfc-7ccae1c362a45b28f4fbf96da4f479730e4b382b.tar
bfc-7ccae1c362a45b28f4fbf96da4f479730e4b382b.tar.gz
bfc-7ccae1c362a45b28f4fbf96da4f479730e4b382b.tar.bz2
bfc-7ccae1c362a45b28f4fbf96da4f479730e4b382b.tar.lz
bfc-7ccae1c362a45b28f4fbf96da4f479730e4b382b.tar.xz
bfc-7ccae1c362a45b28f4fbf96da4f479730e4b382b.tar.zst
bfc-7ccae1c362a45b28f4fbf96da4f479730e4b382b.zip
Initial Commit, probably needs heavy code cleanup
Diffstat (limited to 'src/ivec.c')
-rw-r--r--src/ivec.c119
1 files changed, 119 insertions, 0 deletions
diff --git a/src/ivec.c b/src/ivec.c
new file mode 100644
index 0000000..9c0dd95
--- /dev/null
+++ b/src/ivec.c
@@ -0,0 +1,119 @@
+#include "ivec.h"
+#include <stdio.h>
+#include <stdlib.h>
+
+void iv_free(ivec *v) {
+ free(v->_data);
+ v->_data = NULL;
+ v->_cap = 0;
+ v->len = 0;
+}
+
+static void _iv_ensure_init(ivec *v) {
+ if (v->_data)
+ return;
+
+ v->_cap = 16;
+ v->len = 0;
+
+ v->_data = malloc(v->_cap * sizeof(long long));
+ if (!v->_data) {
+ perror("_v_ensure_init.malloc");
+ abort();
+ }
+}
+
+static void _iv_ensure_capacity(ivec *v) {
+ _iv_ensure_init(v);
+
+ if (v->len >= v->_cap) {
+ v->_cap = (v->_cap == 0) ? 16 : v->_cap * 2;
+
+ long long *tmp = realloc(v->_data, v->_cap * sizeof(long long));
+ if (!tmp) {
+ perror("_v_ensure_capacity.realloc");
+ abort();
+ }
+
+ v->_data = tmp;
+ }
+}
+
+size_t iv_push(ivec *v, long long data) {
+ _iv_ensure_capacity(v);
+
+ v->_data[v->len++] = data;
+ return v->len - 1;
+}
+
+// getter
+long long iv_get(ivec *v, size_t idx) {
+ _iv_ensure_init(v);
+
+ if (idx < v->len) {
+ return v->_data[idx];
+ }
+
+ return 0;
+}
+
+// O(n) shift delete
+long long iv_rem_shift(ivec *v, size_t idx) {
+ _iv_ensure_init(v);
+
+ if (idx >= v->len)
+ return 0;
+
+ int old = v->_data[idx];
+
+ for (size_t j = idx; j + 1 < v->len; j++) {
+ v->_data[j] = v->_data[j + 1];
+ }
+
+ v->len--;
+ return old;
+}
+
+// O(1) swap delete
+long long iv_rem(ivec *v, size_t idx) {
+ _iv_ensure_init(v);
+
+ if (idx >= v->len)
+ return 0;
+
+ int old = v->_data[idx];
+ v->_data[idx] = v->_data[--v->len];
+ return old;
+}
+
+// search
+long long iv_has(ivec *v, long long x,
+ int (*comp)(const long long, const long long)) {
+ _iv_ensure_init(v);
+
+ if (!comp)
+ return 0;
+
+ for (size_t i = 0; i < v->len; i++) {
+ if (comp(v->_data[i], x) == 0) {
+ return v->_data[i];
+ }
+ }
+
+ return 0;
+}
+
+void iv_shrink(ivec *v) {
+ _iv_ensure_init(v);
+
+ size_t new_cap = v->len ? v->len : 1;
+
+ long long *tmp = realloc(v->_data, new_cap * sizeof(int)); // FIX
+ if (!tmp) {
+ perror("v_shrink.realloc");
+ abort();
+ }
+
+ v->_cap = new_cap;
+ v->_data = tmp;
+}