#include #include struct claim { unsigned id; unsigned x; unsigned y; unsigned w; unsigned h; }; struct claim *parseclaims(unsigned *len, const char *fname) { FILE *f = fopen(fname, "r"); if (!f) { perror(fname); return NULL; } GArray *array = g_array_new(FALSE, FALSE, sizeof(struct claim)); *len = 0; char *line = NULL; size_t line_len = 0; while (getline(&line, &line_len, f) != -1) { struct claim claim = {0}; // Haha what is proper parsing sscanf(line, "#%u @ %u,%u: %ux%u", &claim.id, &claim.x, &claim.y, &claim.w, &claim.h ); g_array_append_val(array, claim); (*len)++; } free(line); fclose(f); struct claim *res = (struct claim *)g_array_free(array, FALSE); return res; } int main() { unsigned claims_len; struct claim *claims = parseclaims(&claims_len, "input"); if (!claims) return 1; char (*tilemap)[1000] = g_malloc0(sizeof(char[1000][1000])); for (struct claim *claim = claims; claim < claims + claims_len; claim++) { // Basic sanity check if (claim->y > 1000 || claim->y + claim->h > 1000 || claim->x > 1000 || claim->x + claim->w > 1000) { fprintf(stderr, "Warning: Ignoring out-of-bounds claim: " "#%u @ %u,%u: %ux%u\n", claim->id, claim->x, claim->y, claim->w, claim->h ); continue; } for (unsigned y = claim->y; y < claim->y + claim->h; y++) { for (unsigned x = claim->x; x < claim->x + claim->w; x++) { if (tilemap[y][x] >= 2) continue; tilemap[y][x]++; } } } int tally = 0; for (char *i = *tilemap; i < *tilemap + 1000 * 1000; i++) { if (*i >= 2) tally++; } printf("%d\n", tally); g_free(claims); g_free(tilemap); return 0; }