day16 solution
parent
0cb6fcf521
commit
fbe2635c5b
|
@ -0,0 +1,8 @@
|
|||
all: day16.beam
|
||||
erl -noshell -s day16 start -s init stop
|
||||
|
||||
day16.beam:
|
||||
erlc day16.erl
|
||||
|
||||
clean:
|
||||
rm -f day16.beam
|
|
@ -0,0 +1,68 @@
|
|||
-module(day16).
|
||||
-export([start/0]).
|
||||
|
||||
dance([], Registers)
|
||||
-> Registers;
|
||||
dance([Head|Tail], Registers)
|
||||
-> Instr = string:slice(Head, 0, 1),
|
||||
Args = string:slice(Head, 1),
|
||||
NewRegisters = process_instruction(Instr, Args, Registers),
|
||||
dance(Tail, NewRegisters).
|
||||
|
||||
process_instruction(Instr, Args, Registers)
|
||||
when Instr == <<"s">> -> Len = string:length(Registers),
|
||||
{ Count, _ } = string:to_integer(Args),
|
||||
Index = Len - Count,
|
||||
First = string:slice(Registers, Index),
|
||||
Second = string:slice(Registers, 0, Index),
|
||||
string:concat(First, Second);
|
||||
process_instruction(Instr, Args, Registers)
|
||||
when Instr == <<"x">> -> [FirstRegister|Rest] = re:split(Args, "/"),
|
||||
[SecondRegister|_] = Rest,
|
||||
{ FirstIndex, _ } = string:to_integer(FirstRegister),
|
||||
{ SecondIndex, _ } = string:to_integer(SecondRegister),
|
||||
swap_registers(FirstIndex, SecondIndex, Registers);
|
||||
process_instruction(Instr, Args, Registers)
|
||||
when Instr == <<"p">> -> [FirstRegister|Rest] = re:split(Args, "/"),
|
||||
[SecondRegister|_] = Rest,
|
||||
IndexA = char_index(FirstRegister, Registers),
|
||||
IndexB = char_index(SecondRegister, Registers),
|
||||
swap_registers(IndexA, IndexB, Registers).
|
||||
|
||||
char_index(Char, String)
|
||||
-> StrLen = string:length(String),
|
||||
StrLen - string:length(string:find(String, Char)).
|
||||
|
||||
find_char_index(Index)
|
||||
when Index == nomatch -> 0;
|
||||
find_char_index(Index)
|
||||
-> Index.
|
||||
|
||||
swap_registers(A, B, Registers)
|
||||
when B < A -> swap_registers(B, A, Registers);
|
||||
swap_registers(A, B, Registers)
|
||||
-> RegisterList = list_to_tuple(Registers),
|
||||
ValueA = element(A + 1, RegisterList),
|
||||
ValueB = element(B + 1, RegisterList),
|
||||
tuple_to_list(setelement(B + 1, setelement(A + 1, RegisterList, ValueB), ValueA)).
|
||||
|
||||
dance_countdown(Steps, Instructions, Registers)
|
||||
-> dance_countdown(Steps, Instructions, Registers, Steps, []).
|
||||
|
||||
dance_countdown(Steps, _Instructions, Registers, _OriginalSteps, _PreviousSteps)
|
||||
when Steps == 0 -> Registers;
|
||||
dance_countdown(Steps, Instructions, Registers, OriginalSteps, PreviousSteps)
|
||||
-> CurrentRegisters = dance(Instructions, Registers),
|
||||
Found = lists:any(fun(X) -> string:equal(X, CurrentRegisters) end, PreviousSteps),
|
||||
if Found -> Index = OriginalSteps rem length(PreviousSteps),
|
||||
lists:nth(Index, PreviousSteps);
|
||||
true -> dance_countdown(Steps - 1, Instructions, CurrentRegisters, OriginalSteps, lists:append(PreviousSteps, [CurrentRegisters]))
|
||||
end.
|
||||
|
||||
start()
|
||||
-> SampleInstructions = re:split("s1,x3/4,pe/b", ","),
|
||||
io:fwrite("~p~n", [dance(SampleInstructions, "abcde")]),
|
||||
{ ok, File } = file:read_file("input"),
|
||||
InputInstructions = re:split(unicode:characters_to_list(string:chomp(File)), ","),
|
||||
io:fwrite("~p~n", [dance(InputInstructions, "abcdefghijklmnop")]),
|
||||
io:fwrite("~p~n", [dance_countdown(1000000000, InputInstructions, "abcdefghijklmnop")]).
|
File diff suppressed because one or more lines are too long
Loading…
Reference in New Issue