19a.c (1924B)
1 #include <inttypes.h> 2 #include <stdbool.h> 3 #include <stdio.h> 4 #include <stdlib.h> 5 #include <string.h> 6 7 #define N 1000 8 9 typedef struct { int64_t val[26]; } part_t; 10 typedef struct { char v, comp, wnext[10]; int64_t b; } rule_t; 11 typedef struct { char name[50]; int64_t n; rule_t r[100]; } workflow_t; 12 13 int64_t nw, np, A; 14 workflow_t w[N]; 15 part_t p[N]; 16 17 workflow_t readw(char *buf) { 18 workflow_t ret = {0}; 19 for (int i = 0; *buf != '{'; buf++, i++) 20 ret.name[i] = *buf; 21 for (rule_t r; *buf != '}'; ret.r[ret.n++] = r) { 22 buf++; 23 memset(&r, 0, sizeof(r)); 24 if (*(buf+1) == '<' || *(buf+1) == '>') { 25 r.v = *buf; 26 r.comp = *(buf+1); 27 r.b = atoll(buf+2); 28 while (*buf != ':') buf++; 29 buf++; 30 } 31 for (int i = 0; *buf != ',' && *buf != '}'; buf++, i++) 32 r.wnext[i] = *buf; 33 } 34 return ret; 35 } 36 37 part_t readp(char *buf) { 38 part_t p = {0}; 39 while (*buf != '}') { 40 buf++; 41 p.val[*buf-'a'] = atoll(buf+2); 42 while(*buf != ',' && *buf != '}') buf++; 43 } 44 return p; 45 } 46 47 int64_t value(part_t p) { 48 return p.val['x'-'a'] + p.val['m'-'a'] + p.val['a'-'a'] + p.val['s'-'a']; 49 } 50 51 bool satisfy(part_t p, rule_t r) { 52 if (r.v == 0) return true; 53 int64_t val = p.val[r.v-'a']; 54 return r.comp == '<' ? (val < r.b) : (val > r.b); 55 } 56 57 workflow_t findw(char *name) { 58 for (int i = 0; i < nw; i++) 59 if (!strcmp(name, w[i].name)) 60 return w[i]; 61 printf("Error: workflow %s not found\n", name); 62 exit(1); 63 } 64 65 int main() { 66 char *buf, line[N]; 67 68 for (nw = 0; *(buf = fgets(line, N, stdin)) != '\n'; nw++) 69 w[nw] = readw(buf); 70 71 for (np = 0; (buf = fgets(line, N, stdin)) != NULL; np++) 72 p[np] = readp(buf); 73 74 for (int i = 0; i < np; i++) { 75 workflow_t ww = findw("in"); 76 for (rule_t r; ; ww = findw(r.wnext)) { 77 for (int64_t j = 0; !satisfy(p[i], r = ww.r[j]); j++) ; 78 if (!strcmp("A", r.wnext) || !strcmp("R", r.wnext)) { 79 A += value(p[i]) * (r.wnext[0] == 'A'); 80 break; 81 } 82 } 83 } 84 85 printf("%" PRId64 "\n", A); 86 return 0; 87 }