3
3
#include <stdlib.h>
4
4
#include <string.h>
5
5
6
- const char XMAS [] = "XMAS" ;
7
-
8
6
#define GRID_SIZE 140
9
- #define XMAS_LENGTH (sizeof(XMAS ) / sizeof(char) - 1)
7
+ #define LENGTH ( S ) (sizeof(S ) / sizeof(char) - 1)
10
8
11
9
struct Grid {
12
10
char data [GRID_SIZE ][GRID_SIZE ];
13
11
int width ;
14
12
int height ;
15
13
};
16
14
15
+ struct Solution {
16
+ int part1 ;
17
+ int part2 ;
18
+ };
19
+
17
20
bool in_bounds (struct Grid grid , int i , int j ) {
18
21
return i >= 0 && i < grid .height && j >= 0 && j < grid .width ;
19
22
}
20
23
21
- bool has_xmas_at (struct Grid grid , int i , int j , int di , int dj ) {
22
- for (int k = 0 ; k < XMAS_LENGTH ; k ++ ) {
24
+ bool matches_at (struct Grid grid , int i , int j , int di , int dj , const char pattern [], int length ) {
25
+ for (int k = 0 ; k < length ; k ++ ) {
23
26
int ni = i + k * di ;
24
27
int nj = j + k * dj ;
25
- if (!in_bounds (grid , ni , nj ) || grid .data [ni ][nj ] != XMAS [k ]) {
28
+ if (!in_bounds (grid , ni , nj ) || grid .data [ni ][nj ] != pattern [k ]) {
26
29
return false;
27
30
}
28
31
}
29
32
return true;
30
33
}
31
34
32
- int count_xmas_at (struct Grid grid , int i , int j ) {
33
- return has_xmas_at (grid , i , j , 1 , 0 ) + has_xmas_at (grid , i , j , 0 , 1 )
34
- + has_xmas_at (grid , i , j , -1 , 0 ) + has_xmas_at (grid , i , j , 0 , -1 )
35
- + has_xmas_at (grid , i , j , 1 , 1 ) + has_xmas_at (grid , i , j , -1 , -1 )
36
- + has_xmas_at (grid , i , j , -1 , 1 ) + has_xmas_at (grid , i , j , 1 , -1 );
35
+ bool matches_xmas_at (struct Grid grid , int i , int j , int di , int dj ) {
36
+ const char XMAS [] = "XMAS" ;
37
+ return matches_at (grid , i , j , di , dj , XMAS , LENGTH (XMAS ));
38
+ }
39
+
40
+ int count_xmas1_at (struct Grid grid , int i , int j ) {
41
+ return matches_xmas_at (grid , i , j , 1 , 0 ) + matches_xmas_at (grid , i , j , 0 , 1 )
42
+ + matches_xmas_at (grid , i , j , -1 , 0 ) + matches_xmas_at (grid , i , j , 0 , -1 )
43
+ + matches_xmas_at (grid , i , j , 1 , 1 ) + matches_xmas_at (grid , i , j , -1 , -1 )
44
+ + matches_xmas_at (grid , i , j , -1 , 1 ) + matches_xmas_at (grid , i , j , 1 , -1 );
45
+ }
46
+
47
+ bool matches_mas_at (struct Grid grid , int i , int j , int di , int dj ) {
48
+ const char MAS [] = "MAS" ;
49
+ return matches_at (grid , i , j , di , dj , MAS , LENGTH (MAS ));
50
+ }
51
+
52
+ bool has_xmas2_at (struct Grid grid , int i , int j ) {
53
+ return (matches_mas_at (grid , i - 1 , j - 1 , 1 , 1 ) && matches_mas_at (grid , i + 1 , j - 1 , -1 , 1 ))
54
+ || (matches_mas_at (grid , i + 1 , j - 1 , -1 , 1 ) && matches_mas_at (grid , i + 1 , j + 1 , -1 , -1 ))
55
+ || (matches_mas_at (grid , i - 1 , j - 1 , 1 , 1 ) && matches_mas_at (grid , i - 1 , j + 1 , 1 , -1 ))
56
+ || (matches_mas_at (grid , i - 1 , j + 1 , 1 , -1 ) && matches_mas_at (grid , i + 1 , j + 1 , -1 , -1 ));
37
57
}
38
58
39
59
struct Grid parse_grid (FILE * input ) {
@@ -54,14 +74,15 @@ struct Grid parse_grid(FILE *input) {
54
74
return grid ;
55
75
}
56
76
57
- int count_xmas (struct Grid grid ) {
58
- int count = 0 ;
77
+ struct Solution solve (struct Grid grid ) {
78
+ struct Solution solution = { . part1 = 0 , . part2 = 0 } ;
59
79
for (int i = 0 ; i < grid .height ; i ++ ) {
60
80
for (int j = 0 ; j < grid .width ; j ++ ) {
61
- count += count_xmas_at (grid , i , j );
81
+ solution .part1 += count_xmas1_at (grid , i , j );
82
+ solution .part2 += has_xmas2_at (grid , i , j );
62
83
}
63
84
}
64
- return count ;
85
+ return solution ;
65
86
}
66
87
67
88
int main (int argc , const char * argv []) {
@@ -81,8 +102,9 @@ int main(int argc, const char *argv[]) {
81
102
printf ("Grid is of width %d and height %d\n" , grid .width , grid .height );
82
103
fclose (input );
83
104
84
- int part1 = count_xmas (grid );
85
- printf ("Part 1: %d\n" , part1 );
105
+ struct Solution solution = solve (grid );
106
+ printf ("Part 1: %d\n" , solution .part1 );
107
+ printf ("Part 2: %d\n" , solution .part2 );
86
108
87
109
return 0 ;
88
110
}
0 commit comments