Skip to content

Instantly share code, notes, and snippets.

@rexim
Last active March 14, 2026 22:39
Show Gist options
  • Select an option

  • Save rexim/48d7087bfc8ba2c28a8b0b3aa3183558 to your computer and use it in GitHub Desktop.

Select an option

Save rexim/48d7087bfc8ba2c28a8b0b3aa3183558 to your computer and use it in GitHub Desktop.
Source code from the "Insane Shadow Data Trick in C" YouTube video https://www.youtube.com/watch?v=gtk3RZHwJUA
// cc -o arr arr.c && ./arr
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
typedef struct {
size_t count;
size_t capacity;
} Header;
#define ARR_INIT_CAPACITY 1
#define arr_push(arr, x) \
do { \
if (arr == NULL) { \
Header *header = malloc(sizeof(*arr)*ARR_INIT_CAPACITY + sizeof(Header)); \
header->count = 0; \
header->capacity = ARR_INIT_CAPACITY; \
arr = (void*)(header + 1); \
} \
Header *header = (Header*)(arr) - 1; \
if (header->count >= header->capacity) { \
header->capacity *= 2; \
header = realloc(header, sizeof(*arr)*header->capacity + sizeof(Header)); \
arr = (void*)(header + 1); \
} \
(arr)[header->count++] = (x); \
} while(0)
#define arr_len(arr) ((Header*)(arr) - 1)->count
#define arr_free(arr) free((Header*)(arr) - 1)
int main()
{
float *numbers = NULL;
arr_push(numbers, 69);
arr_push(numbers, 420);
arr_push(numbers, 1337);
arr_push(numbers, 80085);
if (1) arr_push(numbers, 111); else arr_push(numbers, 222);
for (size_t i = 0; i < arr_len(numbers); ++i) {
printf("%f\n", numbers[i]);
}
arr_free(numbers);
return 0;
}
//////////////////////////////
#if 0
#define STB_DS_IMPLEMENTATION
#include "stb_ds.h"
typedef struct {
const char *key;
size_t value;
} Item;
Item *table = NULL;
int main2()
{
shput(table, "foo", 69);
shput(table, "bar", 420);
shput(table, "baz", 1337);
table[shgeti(table, "bar")].value = 80085;
for (int i = 0; i < shlen(table); ++i) {
printf("%s => %zu\n", table[i]);
}
return 0;
}
#endif
@lduguid
Copy link

lduguid commented Mar 3, 2026

interesting, even stranger if i do something like;
https://godbolt.org/z/34qE15hef
that also works with 2 int's as fields of the struct. i have not looked into the assembler to see what is going on under the covers yet between the difference impl.s etc. cheers.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment