summaryrefslogtreecommitdiff
path: root/2015/day23.exs
blob: 433f70a3a985561d34b48b02f26d0d06712f70fc (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
require Integer

program =
  File.stream!("inputs/day23.txt")
  |> Enum.map(&String.trim(&1))

programLength = length(program)

step = fn {programCounter, a, b} ->
  instruction = Enum.at(program, programCounter)

  case instruction do
    "hlf a" ->
      {programCounter + 1, div(a, 2), b}

    "tpl a" ->
      {programCounter + 1, a * 3, b}

    "inc a" ->
      {programCounter + 1, a + 1, b}

    "inc b" ->
      {programCounter + 1, a, b + 1}

    <<"jmp " <> offset::binary>> ->
      {offset, ""} = Integer.parse(offset)
      {programCounter + offset, a, b}

    <<"jie a, " <> offset::binary>> ->
      if Integer.is_even(a) do
        {offset, ""} = Integer.parse(offset)
        {programCounter + offset, a, b}
      else
        {programCounter + 1, a, b}
      end

    <<"jio a, " <> offset::binary>> ->
      if a == 1 do
        {offset, ""} = Integer.parse(offset)
        {programCounter + offset, a, b}
      else
        {programCounter + 1, a, b}
      end
  end
end

{_, _, terminalState1} =
  Stream.iterate({0, 0, 0}, &step.(&1))
  |> Enum.find(fn {programCounter, _, _} -> programCounter >= programLength end)

IO.puts("Part 1: #{terminalState1}")

{_, _, terminalState2} =
  Stream.iterate({0, 1, 0}, &step.(&1))
  |> Enum.find(fn {programCounter, _, _} -> programCounter >= programLength end)

IO.puts("Part 2: #{terminalState2}")