#include #include #include #include #include #include #include #include int ID_OFFSET; struct Round { int red; int green; int blue; }; struct Game { struct Round rounds[10]; int iterator; int id; }; struct Games { struct Game games[100]; int iterator; }; int str_to_int(char *str) { int result; char *tmp; result = strtol(str, &tmp, 10); return result; } char *parse_cube(char *line, int *cube_num) { const char delim[2] = " "; char *save_ptr; char *token; token = strtok_r(line, delim, &save_ptr); *cube_num = str_to_int(token); token = strtok_r(NULL, delim, &save_ptr); return token; // Cube colour } struct Round parse_round(char *line, struct Game game) { const char delim[2] = ","; char *save_ptr; char *token; int cube_num; struct Round round = {0, 0, 0}; token = strtok_r(line, delim, &save_ptr); while (token != NULL) { char *colour = parse_cube(token, &cube_num); if (!strcmp(colour, "red")) { round.red = cube_num; } else if (!strcmp(colour, "blue")) { round.blue = cube_num; } else if (!strcmp(colour, "green")) { round.green = cube_num; } token = strtok_r(NULL, delim, &save_ptr); game.rounds[game.iterator] = round; } return round; } struct Game parse_game_data(char *line, struct Game game, int id) { // printf("%s\n", line); // https://www.tutorialspoint.com/c_standard_library/c_function_strtok.htm // https://www.tutorialspoint.com/data_structures_algorithms/hash_table_program_in_c.htm char *token; char *save_ptr; const char delim[2] = ";"; game.id = id; token = strtok_r(line, delim, &save_ptr); while (token != NULL) { game.rounds[game.iterator++] = parse_round(token, game); token = strtok_r(NULL, delim, &save_ptr); } return game; } int get_id(char *ptr) { int id; char *_id = (char *)malloc(4); for (int i = 0; i <= 4; i++) { if (ptr[i] != ':') { _id[i] = ptr[i]; } else { ID_OFFSET = i; break; } } id = str_to_int(_id); return id; } int main() { struct Games games; games.iterator = 0; int MAX_RED = 12; int MAX_GREEN = 13; int MAX_BLUE = 14; int GAME_OFFSET = 5; // Skip the word Game and start on the ID number const char *inputFile = "input"; int fd = open(inputFile, O_RDONLY); if (fd < 0) { printf("\n\"%s \" could not open\n"); exit(1); } struct stat statbuf; int err = fstat(fd, &statbuf); if (err < 0) { printf("\n\"%s \" could not open\n", inputFile); exit(2); } char *ptr = mmap(NULL, statbuf.st_size, PROT_READ, MAP_SHARED, fd, 0); if (ptr == MAP_FAILED) { printf("Mapping failed"); return 1; } int inLine = 0; for (int i = 0; i < statbuf.st_size; i++) { int id; char *tmpLine = (char *)malloc(255); for (int j = 0; j < __INT64_MAX__; j++) { if (inLine == 0) { inLine = 1; i += GAME_OFFSET; id = get_id(&ptr[i]); i += ID_OFFSET + 1; continue; } if (ptr[i + j] == '\n') { memcpy(tmpLine, &ptr[i], j); // printf("ID: %i |", id); struct Game game = {-1, -1}; games.games[games.iterator++] = parse_game_data(tmpLine, game, id); i += j; break; } tmpLine[j] = ptr[i + j]; } inLine = 0; } int total = 0; for (int i = 0; i < games.iterator; i++) // Iterate through the games { int failed = 0; for (int j = 0; j < games.iterator; j++) // Iterate thrugh the rounds { if (games.games[i].rounds[j].red > 12 || games.games[i].rounds[j].blue > 14 || games.games[i].rounds[j].green > 13) { failed = 1; } if (j == games.games[i].iterator) { break; } } if (failed == 0) { total += games.games[i].id; } } printf("\nThe total is: %i\n\n", total); err = munmap(ptr, statbuf.st_size); if (err != 0) { printf("Unmapping failed"); return 1; } return 0; }