advent2022

Advent of Code 2022 Solutions
git clone https://todayiwilllaunchmyinfantsonintoorbit.com/advent2022.git
Log | Files | Refs

ten.erl (2220B)


      1 -module(ten).
      2 
      3 -export([solve/0]).
      4 
      5 %% Run the solution
      6 solve() ->
      7     {ok, In} = file:open("input", read),
      8     Instructions = read_instructions(In),
      9     file:close(In),
     10     {_, Signal, Display} = execute(Instructions),
     11     io:format("Signal strength: ~B~n", [Signal]),
     12     io:format(Display).
     13 
     14 read_instructions(Dev) ->
     15     read_instructions(Dev, []).
     16 
     17 read_instructions(Dev, List) ->
     18     case file:read_line(Dev) of
     19         {ok, Line} ->
     20             read_instructions(Dev, [string:trim(Line)|List]);
     21         eof ->
     22             lists:reverse(List);
     23         {error, badarg} ->
     24             false
     25     end.
     26 
     27 execute(List) ->
     28     execute(List, 1, 1, 0, "").
     29 
     30 execute([], X, _, Signal, Display) ->
     31     {X, Signal, Display};
     32 execute([Ins|Rest], X, Timer, Signal, Display) ->
     33     %% io:fwrite("  Instruction: ~s, X: ~B, Timer: ~B, Signal: ~B~n", [Ins, X, Timer, Signal]),
     34     [Command|Tail] = string:split(Ins, " "),
     35     case Command of
     36         "noop" ->
     37             {NewTimer, NewSignal, NewX, NewDisplay} = timer_tick({Timer, Signal, X, Display});
     38         "addx" ->
     39             {NewTimer, NewSignal, TempX, NewDisplay} = timer_tick(timer_tick({Timer, Signal, X, Display})),
     40             [NStr|_] = Tail,
     41             {N,_} = string:to_integer(NStr),
     42             NewX = TempX + N
     43     end,
     44     execute(Rest, NewX, NewTimer, NewSignal, NewDisplay).
     45 
     46 timer_tick({Timer, Signal, X, Display}) ->
     47     Pixel = (Timer - 1) rem 40,
     48     NewDisplay = draw_pixel_and_advance(Display, Pixel, X),
     49     if (Timer == 20) orelse ((Timer - 20) rem 40 == 0) ->
     50             %% io:fwrite("Timer: ~B, X: ~B, New Signal: ~B~n", [Timer, X, Signal + (Timer * X)]),
     51             {Timer + 1, Signal + (Timer * X), X, NewDisplay};
     52        true ->
     53             {Timer + 1, Signal, X, NewDisplay}
     54     end.
     55 
     56 draw_pixel_and_advance(Display, Pixel, Sprite) ->
     57     NextPixel = next_pixel(Pixel, Sprite),
     58     if (Pixel + 1) rem 40 == 0 ->
     59             DispList = [Display, NextPixel, "~n"];
     60        true ->
     61             DispList = [Display, NextPixel]
     62     end,
     63     unicode:characters_to_list(DispList, unicode).
     64 
     65 next_pixel(Pixel, Sprite) ->
     66     if (Pixel >= (Sprite - 1)) andalso (Pixel =< (Sprite + 1)) ->
     67             "#";
     68        true ->
     69             "."
     70     end.
     71