From de24a05dc18639b1223afaa441c6b35006d63631 Mon Sep 17 00:00:00 2001 From: nalydmerc Date: Tue, 5 Dec 2023 21:19:11 -0500 Subject: [PATCH] Complete Day 5 Part 1 --- 05/05.c | 285 +++++++++++++++++++++++++++++++++++++++++++++++++++-- 05/llist.c | 127 ------------------------ 05/llist.h | 35 ------- 3 files changed, 275 insertions(+), 172 deletions(-) delete mode 100644 05/llist.c delete mode 100644 05/llist.h diff --git a/05/05.c b/05/05.c index fde24af..54052f4 100644 --- a/05/05.c +++ b/05/05.c @@ -1,28 +1,258 @@ #include #include +#include #include -#include "llist.h" #define DEFAULT_FILE "input.txt" -#define STRBUF_LEN 200 +#define STRBUF_LEN 300 #define ISDIGIT(X) (X >= '0' && X <= '9') -uint64_t parse_digit(char *str); +#define ADVENT_MAP_PRINT(X) do {printf("Dest: %d Src: %d Len: %d\n", X.dest, X.src, X.len);} while (0); + +#define ADVENT_MAP_EQ(X,Y) (X.dest == Y.dest && X.src == Y.src && X.len == Y.len) + +/********************************************************/ +// Linked List Functions +/********************************************************/ + +// Node structure +typedef struct ll_node { + void *data; + struct ll_node *next; +} ll_node; + +// Linked list structure +typedef struct linked_list { + ll_node* head; +} linked_list; + +void ll_init(linked_list* list) { + list->head = NULL; +} + +// Function to create a new node +ll_node* ll_create_node(void *data) { + ll_node* new_node = (ll_node*)malloc(sizeof(ll_node)); + if (new_node != NULL) { + new_node->data = data; + new_node->next = NULL; + } + return new_node; +} + +// Function to add a node to the beginning of the list +void ll_prepend(linked_list* list, void *data) { + ll_node* new_node = ll_create_node(data); + if (new_node != NULL) { + new_node->next = list->head; + list->head = new_node; + } +} + +// Function to add a node to the end of the list +void ll_append(linked_list* list, void *data) { + ll_node* newNode = ll_create_node(data); + if (newNode != NULL) { + if (list->head == NULL) { + list->head = newNode; + } else { + ll_node* current = list->head; + while (current->next != NULL) { + current = current->next; + } + current->next = newNode; + } + } +} + +// Function to remove a node with a given value +void ll_remove(linked_list* list, void *data, bool (*compare_function)(void *, void*)) { + ll_node* current = list->head; + ll_node* prev = NULL; + + while (current != NULL && !compare_function(current->data, data)) { + prev = current; + current = current->next; + } + + if (current != NULL) { + if (prev != NULL) { + prev->next = current->next; + } else { + list->head = current->next; + } + free(current); + } +} + +// Function to free the memory used by the linked list +void ll_free(linked_list* list) { + ll_node* current = list->head; + ll_node* next; + + while (current != NULL) { + next = current->next; + free(current->data); + free(current); + current = next; + } + + list->head = NULL; +} + +uint64_t ll_len(linked_list* list) +{ + uint64_t len = 0; + ll_node *current = list->head; + while (current != NULL) + { + len++; + current = current->next; + } + + return len; +} + +/********************************************************/ +// Seeds +/********************************************************/ + +typedef struct advent_map { + uint64_t dest; + uint64_t src; + uint64_t len; +} advent_map; + +uint64_t parse_num(char *str) +{ + uint64_t num = 0; + while (ISDIGIT(*str)) + { + num = (num * 10) + (*str - '0'); + str++; + } + + return num; +} linked_list parse_seeds(char *str) { linked_list seeds; ll_init(&seeds); - while (!ISDIGIT(str)) str++; + while (!ISDIGIT(*str)) str++; - while (*str != '\n') + while (ISDIGIT(*str)) { - uint64_t seed = parse_digit(str); - + uint64_t *seed = malloc(sizeof(uint64_t)); + *seed = parse_num(str); + ll_append(&seeds, seed); + while (ISDIGIT(*str)) str++; + if (*str == ' ') str++; + } + + return seeds; +} + +void print_seeds(linked_list *list) +{ + ll_node* current = list->head; + while (current != NULL) { + printf("Num: %lud\n", *((uint64_t *)(current->data))); + current = current->next; + } + printf("\n"); +} + +uint64_t seed_min(linked_list *list) +{ + ll_node* current = list->head; + if (current == NULL) return 0; + + uint64_t current_val = *(uint64_t *)(current->data); + uint64_t min = current_val; + + while (current != NULL) { + current_val = *(uint64_t *)(current->data); + if (current_val < min) min = current_val; + current = current->next; + } + return min; +} + +/********************************************************/ +// Maps +/********************************************************/ + +void parse_map(linked_list *map, FILE *file) +{ + char *strbuf = malloc(sizeof(char) * STRBUF_LEN); + char *str = strbuf; + + fgets(strbuf, STRBUF_LEN, file); + + while (ISDIGIT(*strbuf)) + { + str = strbuf; + advent_map *map_node = malloc(sizeof(advent_map)); + + map_node->dest = parse_num(str); + while (ISDIGIT(*str)) str++; + str++; + + map_node->src = parse_num(str); + while (ISDIGIT(*str)) str++; + str++; + + map_node->len = parse_num(str); + + ll_append(map, map_node); + if (!fgets(strbuf, STRBUF_LEN, file)) break; } } +void print_map(linked_list *list) +{ + ll_node* current = list->head; + advent_map *m; + while (current != NULL) { + m = (advent_map *)(current->data); + printf("dest: %lu src: %lu len: %lu\n", m->dest, m->src, m->len); + current = current->next; + } + printf("\n"); +} + +uint64_t translate(linked_list *map, uint64_t value) +{ + ll_node *current_node = map->head; + while (current_node != NULL) + { + advent_map *current_map = (advent_map *)current_node->data; + if (value - current_map->src < current_map->len) + { + return current_map->dest + (value - current_map->src); + } + current_node = current_node->next; + } + + return value; +} + +void translate_all(linked_list *map, linked_list *seeds) +{ + ll_node *current_node = seeds->head; + + while (current_node != NULL) + { + uint64_t current_int = *((uint64_t *)(current_node->data)); + uint64_t translated_int = translate(map, current_int); + *((uint64_t *)(current_node->data)) = translated_int; + current_node = current_node->next; + } +} + + int main(int argc, char **argv) { // Get filename as an argument, if there is one @@ -43,12 +273,47 @@ int main(int argc, char **argv) return 1; } + linked_list seeds; - while (fgets(strbuf, STRBUF_LEN, file)) + linked_list seed_to_soil; + linked_list soil_to_fertilizer; + linked_list fertilizer_to_water; + linked_list water_to_light; + linked_list light_to_temperature; + linked_list temperature_to_humidity; + linked_list humidity_to_location; + + linked_list *maps[7] = {&seed_to_soil, + &soil_to_fertilizer, + &fertilizer_to_water, + &water_to_light, + &light_to_temperature, + &temperature_to_humidity, + &humidity_to_location }; + + uint64_t i = 0; + for (i = 0; i < 7; i++) { - // Code goes here - + ll_init(maps[i]); } + fgets(strbuf, STRBUF_LEN, file); + seeds = parse_seeds(strbuf); + fgets(strbuf, STRBUF_LEN, file); + + for (i = 0; i < 7; i++) + { + fgets(strbuf, STRBUF_LEN, file); + printf(strbuf); + parse_map(maps[i], file); + print_map(maps[i]); + translate_all(maps[i], &seeds); + } + + print_seeds(&seeds); + + uint64_t min = seed_min(&seeds); + printf("Min: %lu\n", min); + return 0; } \ No newline at end of file diff --git a/05/llist.c b/05/llist.c deleted file mode 100644 index 6b0ee31..0000000 --- a/05/llist.c +++ /dev/null @@ -1,127 +0,0 @@ -#include -#include -#include "llist.h" - -void ll_init(linked_list* list) { - list->head = NULL; -} - -// Function to create a new node -advent_node* ll_create_node(advent_map map) { - advent_node* new_node = (advent_node*)malloc(sizeof(advent_node)); - if (new_node != NULL) { - new_node->map = map; - new_node->next = NULL; - } - return new_node; -} - -// Function to add a node to the beginning of the list -void ll_prepend(linked_list* list, advent_map map) { - advent_node* new_node = ll_create_node(map); - if (new_node != NULL) { - new_node->next = list->head; - list->head = new_node; - } -} - -// Function to add a node to the end of the list -void ll_append(linked_list* list, advent_map map) { - advent_node* newNode = ll_create_node(map); - if (newNode != NULL) { - if (list->head == NULL) { - list->head = newNode; - } else { - advent_node* current = list->head; - while (current->next != NULL) { - current = current->next; - } - current->next = newNode; - } - } -} - -// Function to remove a node with a given value -void ll_remove(linked_list* list, advent_map map) { - advent_node* current = list->head; - advent_node* prev = NULL; - - while (current != NULL && !ADVENT_MAP_EQ(current->map, map)) { - prev = current; - current = current->next; - } - - if (current != NULL) { - if (prev != NULL) { - prev->next = current->next; - } else { - list->head = current->next; - } - free(current); - } -} - -// Function to print the linked list -void ll_print(linked_list* list) { - advent_node* current = list->head; - while (current != NULL) { - ADVENT_MAP_PRINT(current->map); - current = current->next; - } - printf("\n"); -} - -// Function to free the memory used by the linked list -void ll_free(linked_list* list) { - advent_node* current = list->head; - advent_node* next; - - while (current != NULL) { - next = current->next; - free(current); - current = next; - } - - list->head = NULL; -} - -#if 0 - -// Example usage -int main() { - linked_list myList; - ll_init(&myList); - - advent_map map1; - map1.dest = 1; - map1.src = 50; - map1.len = 5; - - advent_map map2; - map2.dest = 60; - map2.src = 500; - map2.len = 2; - - advent_map map3; - map3.dest = 800; - map3.src = 8000; - map3.len = 5; - - ll_append(&myList, map1); - ll_append(&myList, map2); - ll_append(&myList, map3); - - printf("Original List: \n"); - ll_print(&myList); - - ll_remove(&myList, map2); - - printf("List after removing 2: \n"); - ll_print(&myList); - - ll_free(&myList); - - return 0; -} - -#endif \ No newline at end of file diff --git a/05/llist.h b/05/llist.h deleted file mode 100644 index 26f8f63..0000000 --- a/05/llist.h +++ /dev/null @@ -1,35 +0,0 @@ -#ifndef LLIST_H -#define LLIST_H - -#include - -#define ADVENT_MAP_PRINT(X) do {printf("Dest: %d Src: %d Len: %d\n", X.dest, X.src, X.len);} while (0); - -#define ADVENT_MAP_EQ(X,Y) (X.dest == Y.dest && X.src == Y.src && X.len == Y.len) - -typedef struct advent_map { - uint64_t dest; - uint64_t src; - uint64_t len; -} advent_map; - -// Node structure -typedef struct advent_node { - advent_map map; - struct advent_node *next; -} advent_node; - -// Linked list structure -typedef struct linked_list { - advent_node* head; -} linked_list; - -void ll_init(linked_list* list); -void ll_prepend(linked_list* list, advent_map map); -void ll_append(linked_list* list, advent_map map); -void ll_remove(linked_list* list, advent_map map); -void ll_print(linked_list* list); -void ll_free(linked_list* list); - - -#endif \ No newline at end of file