]> fbox.kageds.com Git - adventofcode.git/blob - 2021/day5/day5.erl
day11
[adventofcode.git] / 2021 / day5 / day5.erl
1 %% to compile: erlc day3A.erl
2 %% to run: erl -noshell -s day5 solve
3 %%
4 -module(day5).
5
6 -export ([solve/0, solve/1, solve/2]).
7 -export ([read_input/0]).
8
9 solve() ->
10 solve(['1']),
11 solve(['2']),
12 init:stop().
13
14 solve(A) ->
15 solve(A, read_input()).
16
17 solve(['1'], D) ->
18 io:format("The solution to ~p puzzle1 is: ~p~n", [?MODULE, solve(1, D)]);
19 solve(1, D) ->
20 solution1(D);
21 solve(['2'], D) ->
22 io:format("The solution to ~p puzzle2 is: ~p~n", [?MODULE, solve(2, D)]);
23 solve(2, D) ->
24 solution2(D).
25
26 read_input() ->
27 {ok, IO} = file:open("input.txt", 'read'),
28 Data = read_input(IO),
29 file:close(IO),
30 Data.
31
32 read_input(IO) ->
33 read_input(IO, []).
34
35 read_input(IO, Input) ->
36 case read_line(IO) of
37 'eof' ->
38 lists:map(fun([{X1,Y1},{X2,Y2}]) ->
39 case X1 > X2 orelse (X1 == X2 andalso Y1 > Y2) of
40 'true' -> [{X2,Y2},{X1,Y1}];
41 'false' -> [{X1,Y1},{X2,Y2}]
42 end
43 end, Input);
44 Line -> read_input(IO, Input ++ [Line])
45 end.
46
47 read_line(IO) ->
48 case file:read_line(IO) of
49 'eof' -> 'eof';
50 {ok, Line} -> parse_line(Line)
51 end.
52
53 parse_line(Line) ->
54 Points = string:tokens(Line, " ,->\n"),
55 [X1, Y1, X2, Y2] = [list_to_integer(X) || X <- Points],
56 [{X1, Y1},{X2,Y2}].
57
58 solution1(Input) ->
59 HV = get_hor_vert(Input),
60 Points = lists:sort(
61 lists:flatten(
62 [[{X,Y} || X <- lists:seq(X1, X2, case X1 =< X2 of 'true' -> 1; _ -> -1 end),
63 Y <- lists:seq(Y1, Y2, case Y1 =< Y2 of 'true' -> 1; _ -> -1 end)] || [{X1,Y1},{X2,Y2}] <- HV]
64 )
65 ),
66 Count = count_duplicates(Points),
67 Count.
68
69 solution2(Input) ->
70 Points = get_all_points(Input),
71 Count = count_duplicates(lists:sort(Points)),
72 Count.
73
74
75 get_hor_vert(Input) ->
76 lists:filter(fun([{X1, Y1},{X2,Y2}]) -> X1 == X2 orelse Y1 == Y2 end, Input).
77
78 get_all_points(Input) ->
79 get_all_points(Input, []).
80
81 get_all_points([], Acc) ->
82 Acc;
83 get_all_points([[{X1,Y1},{X2,Y2}]|Rest], Acc) when X1 == X2 ->
84 get_all_points(Rest, Acc ++ [{X1, Y} || Y <- lists:seq(Y1,Y2)]);
85 get_all_points([[{X1,Y1},{X2,Y2}]|Rest], Acc) when Y1 == Y2 ->
86 get_all_points(Rest, Acc ++ [{X, Y1} || X <- lists:seq(X1,X2)]);
87 get_all_points([[{X1,Y1},{X2,Y2}]|Rest], Acc) when Y1 < Y2 ->
88 get_all_points(Rest, Acc ++ [{X, Y1-X1+X} || X <- lists:seq(X1,X2)]);
89 get_all_points([[{X1,Y1},{X2,Y2}]|Rest], Acc) when Y1 > Y2 ->
90 get_all_points(Rest, Acc ++ [{X, (-1 * X) + X1 + Y1 } || X <- lists:seq(X1,X2)]).
91
92 count_duplicates(Points) ->
93 count_duplicates(Points, []).
94
95 count_duplicates([], Count) ->
96 lists:foldl(fun({X, _P}, Acc) ->
97 case X > 1 of 'true' -> Acc + 1; _ -> Acc end end, 0, Count);
98 count_duplicates([H|T], Count) ->
99 case T /= [] andalso hd(T) == H of
100 'true' -> count_duplicate(H, T, Count, 1);
101 _Else -> count_duplicates(T, Count ++ [{1, H}])
102 end.
103
104 count_duplicate(H, [H|T], Count, X) ->
105 count_duplicate(H, T, Count, X + 1);
106 count_duplicate(H, List, Count, X) ->
107 count_duplicates(List, Count ++ [{X, H}]).
108
109
110