11const std = @import ("std" );
22const HashMap = std .AutoArrayHashMap ;
33const Allocator = std .mem .Allocator ;
4+ const string = []const u8 ;
45
56/// Task 1
6- pub fn solution_1 (contents : [] const u8 ) ! usize {
7+ pub fn solution_1 (contents : string ) ! usize {
78 var arena = std .heap .ArenaAllocator .init (std .heap .page_allocator );
89 defer arena .deinit ();
910
1011 const allocator = arena .allocator ();
11- const setup = try parse_map (contents , allocator );
12- const map = setup [0 ];
13- var guard = setup [1 ];
12+ const map , var guard = try parse_map (contents , allocator );
1413
14+ // Move the guard until it is outside the map and record all positions
1515 var visited = HashMap (Position , void ).init (allocator );
1616 while (is_guard_inside (map , guard )) : (guard = move (map , guard )) {
1717 try visited .put (guard .pos , {});
@@ -21,36 +21,35 @@ pub fn solution_1(contents: []const u8) !usize {
2121}
2222
2323/// Task 2
24- pub fn solution_2 (contents : [] const u8 ) ! usize {
24+ pub fn solution_2 (contents : string ) ! usize {
2525 var arena = std .heap .ArenaAllocator .init (std .heap .page_allocator );
2626 defer arena .deinit ();
2727
2828 const allocator = arena .allocator ();
29- const setup = try parse_map (contents , allocator );
30- var map = setup [0 ];
31- var guard = setup [1 ];
29+ var map , var guard = try parse_map (contents , allocator );
3230
31+ // Move the guard until it is outside the map and record all states
3332 var visited = HashMap (Guard , void ).init (allocator );
3433 while (is_guard_inside (map , guard )) : (guard = move (map , guard )) {
3534 try visited .put (guard , {});
3635 }
3736
38- var tried_obstacle = HashMap (Position , void ).init (allocator );
39- try tried_obstacle .put (visited .keys ()[0 ].pos , {});
37+ var new_obstacles = HashMap (Position , void ).init (allocator );
38+ try new_obstacles .put (visited .keys ()[0 ].pos , {});
4039 var loop_count : usize = 0 ;
40+
41+ // Put an obstacle into each unique position in the guards path and check
42+ // wether the guard runs in a loop or exits the map
4143 for (0.. visited .count ()) | i | {
42- if (tried_obstacle .contains (visited .keys ()[i ].pos )) {
44+ if (new_obstacles .contains (visited .keys ()[i ].pos )) {
4345 continue ;
4446 }
45-
4647 try map .obstacles .put (visited .keys ()[i ].pos , {});
4748
49+ // Let the guard start right in front of the new obstacle to save time
4850 guard = visited .keys ()[i - 1 ];
49- var states = HashMap (Guard , void ).init (
50- std .heap .page_allocator ,
51- );
52- defer states .deinit ();
5351
52+ var states = HashMap (Guard , void ).init (allocator );
5453 while (is_guard_inside (map , guard )) : (guard = move (map , guard )) {
5554 if (states .contains (guard )) {
5655 loop_count += 1 ;
@@ -60,7 +59,7 @@ pub fn solution_2(contents: []const u8) !usize {
6059 }
6160
6261 _ = map .obstacles .pop ();
63- try tried_obstacle .put (visited .keys ()[i ].pos , {});
62+ try new_obstacles .put (visited .keys ()[i ].pos , {});
6463 }
6564
6665 return loop_count ;
@@ -131,7 +130,7 @@ pub fn is_guard_inside(map: GuardMap, guard: Guard) bool {
131130///
132131/// Returns:
133132/// - Array list of report objects.
134- fn parse_map (contents : [] const u8 , allocator : Allocator ) ! struct { GuardMap , Guard } {
133+ fn parse_map (contents : string , allocator : Allocator ) ! struct { GuardMap , Guard } {
135134 var obstacles = HashMap (Position , void ).init (allocator );
136135 var dir : ? Direction = null ;
137136 var pos : ? Position = null ;
0 commit comments