This topic is about Day 21 of the Advent of Code 2021 .
We have a private leaderboard (shared with users of the elixir forum):
https://adventofcode.com/2021/leaderboard/private/view/370884
The entry code is:
370884-a6a71927
This topic is about Day 21 of the Advent of Code 2021 .
We have a private leaderboard (shared with users of the elixir forum):
https://adventofcode.com/2021/leaderboard/private/view/370884
The entry code is:
370884-a6a71927
Part1 was simple enough; my solution doesn’t lend itself to part 2
-compile([export_all]).
-record(state, { die_num = 1,
next_pid,
pos ,
score = 0,
die_roll =0
}).
%% Not reading in input just setting positions.
-define(P1_START, 1).
-define(P2_START, 10).
p1() ->
process_flag(trap_exit, true),
{ok,P1Pid} = proc_lib:start_link(?MODULE, init, [self(), player1,?P1_START]),
{ok, P2Pid }= proc_lib:start_link(?MODULE, init, [self(), player2,?P2_START]),
P1Pid ! {set, P2Pid},
P2Pid ! {set, P1Pid},
P1Pid ! {run, 1, 0},
{P1Pid, P2Pid}.
init(PPid, Name, StartPos) ->
proc_lib:init_ack(PPid, {ok, self()}),
register(Name, self()),
loop(#state{pos = StartPos}).
loop(shutdown) ->
void;
loop(State) ->
NewState = receive
Msg -> process_msg(Msg, State)
end,
loop(NewState).
process_msg({set, Pid} , State) ->
State#state{next_pid = Pid};
process_msg({run, Die, Rolls}, State= #state{next_pid = NPid}) ->
Roll = Die * 3 + 3,
NewDieCount = Die + 3,
NewRolls = Rolls + 3,
case score(Roll, State) of
{N, _} when N >= 1000 ->
%% Win
NPid ! {lose, NewRolls},
shutdown;
{N,NewPos} ->
NPid ! {run, NewDieCount, NewRolls},
State#state{score = N,
pos = NewPos
}
end;
process_msg({lose, NewDieCount}, _State = #state{score = Score}) ->
Output = NewDieCount * Score,
io:format("Answer:~p~n", [Output]),
shutdown.
score(Roll, #state{ pos = Pos,
score = Score }) ->
CurPos = Pos+Roll,
NPos = make_1_to_10(CurPos),
{NPos + Score, NPos}.
%% Sure there is better way.
make_1_to_10(N) when N >=1,
N =< 10 ->
N;
make_1_to_10(N) -> make_1_to_10(N-10).