summaryrefslogtreecommitdiff
path: root/2024/10/1.c
diff options
context:
space:
mode:
authorkaa <kaa@disroot.org>2025-06-18 03:01:46 -0700
committerkaa <kaa@disroot.org>2025-06-18 03:01:46 -0700
commiteb1be90b94a1449e0444e7d912d5ccf314b5f10f (patch)
tree7a4be272df182576a6b70486a4d90bdac0ada5ec /2024/10/1.c
parentf7c2841cdd3d5854ad4a1a53cb9627f4ba8dc805 (diff)
AOC 2024/10
Diffstat (limited to '2024/10/1.c')
-rw-r--r--2024/10/1.c177
1 files changed, 177 insertions, 0 deletions
diff --git a/2024/10/1.c b/2024/10/1.c
new file mode 100644
index 0000000..a8112a6
--- /dev/null
+++ b/2024/10/1.c
@@ -0,0 +1,177 @@
+#include <stdio.h>
+#include <stdbool.h>
+#include "../../d.h"
+#include "map.h"
+
+bool debug = true;
+
+typedef struct {
+ int width;
+ int height;
+ char** e;
+ bool** visited;
+} Graph2D;
+
+enum {
+ NORTH = 0, EAST, SOUTH, WEST, DIRECTIONS,
+};
+
+/* Reads from the input until exhausted. Returns memory which must be
+freed by the caller. */
+Graph2D*
+ingest(FILE* in)
+{
+ char *t = getall(in);
+ char *s = t;
+
+ /* Two passes. One to count width and height.
+ Another to store to allocated memory. */
+ int height = 0, width = -1, i = 0;
+ while (s[i] != '\0') {
+ if (s[i] == '\n') {
+ if (width == -1) {
+ width = i + 1;
+ }
+ height++;
+ }
+ i++;
+ }
+ char** buffer = calloc(height, sizeof(char*));
+ bool** visited = calloc(height, sizeof(bool*));
+
+ Graph2D* g = calloc(1, sizeof(Graph2D));
+ g->width = width;
+ g->height = height;
+ g->e = buffer;
+ g->visited = visited;
+
+ i = height;
+ while (i > 0) {
+ buffer[i-1] = calloc(width, sizeof(char));
+ visited[i-1] = calloc(width, sizeof(bool));
+ i--;
+ }
+
+ i = 0;
+ int j = 0;
+ while (i < height) {
+ if (j < width - 1) {
+ buffer[i][j] = *s;
+ j++;
+ } else {
+ i++;
+ j = 0;
+ }
+ s++;
+ }
+
+ free(t);
+ return g;
+}
+
+typedef struct {
+ int x;
+ int y;
+} Coordinates;
+
+typedef struct Stack {
+ void* value;
+ struct Stack* below;
+} Stack;
+
+Stack*
+pop(Stack* s) {
+ free(s->value);
+ Stack* tmp = s->below;
+ free(s);
+ return tmp;
+}
+Stack*
+push(Stack* s, void* value) {
+ Stack* t = calloc(1, sizeof(Stack));
+ t->below = s;
+ t->value = value;
+ return t;
+}
+
+bool
+valid(Graph2D* g, Coordinates c)
+{
+ return c.x >= 0 && c.x < g->width && c.y >= 0 && c.y < g->height;
+}
+
+int score = 0;
+void
+travel(Graph2D* g, Coordinates c)
+{
+ // g->visited[c.y][c.x] = true;
+
+ if (debug) {
+ printf("%d,%d\n", c.x, c.y);
+ printf("%c\n", g->e[c.y][c.x]);
+ }
+
+ Coordinates cardinal[DIRECTIONS];
+ cardinal[SOUTH] = (Coordinates) {c.x, c.y + 1};
+ cardinal[NORTH] = (Coordinates) {c.x, c.y - 1};
+ cardinal[EAST] = (Coordinates) {c.x + 1, c.y};
+ cardinal[WEST] = (Coordinates) {c.x - 1, c.y};
+
+ if (g->e[c.y][c.x] == '9') {
+ score++;
+ return;
+ }
+ for (int i = 0; i < DIRECTIONS; i++) {
+ if (valid(g, cardinal[i])) {
+ if (debug) {
+ printf("%d,%d\n", cardinal[i].x, cardinal[i].y);
+ printf("%d\n", g->e[cardinal[i].y][cardinal[i].x]);
+ printf("-\n");
+ printf("%d\n", g->e[c.y][c.x]);
+ printf("%d\n", g->e[cardinal[i].y][cardinal[i].x] - g->e[c.y][c.x]);
+ }
+
+ if (g->e[cardinal[i].y][cardinal[i].x] - g->e[c.y][c.x] == 1) {
+ if (debug) {
+ printf("Valid: %d,%d\n", cardinal[i].x, cardinal[i].y);
+ }
+ travel(g, cardinal[i]);
+ }
+ }
+ }
+ return;
+}
+
+int
+main()
+{
+ FILE* in = fopen("sample_small", "r");
+ if (in == NULL) {
+ exit(1);
+ }
+
+ Graph2D* g = ingest(in);
+
+ for (int i = 0; i < g->height; i++) {
+ for (int j = 0; j < g->width; j++) {
+ if (g->e[i][j] == '0') {
+ travel(g, (Coordinates) {j, i});
+ // Score is a global
+ printf("%d\n", score);
+ }
+ }
+ }
+
+ for (int i = 0; i < g->height; i++) {
+ for (int j = 0; j < g->width; j++) {
+ printf("%c", g->e[i][j]);
+ }
+ putchar('\n');
+ free(g->e[i]);
+ free(g->visited[i]);
+ }
+ free(g->e);
+ free(g->visited);
+ free(g);
+ return 0;
+}