diff --git a/2023/lib/2023/8.ex b/2023/lib/2023/8.ex index c6d37a1..40bffa5 100644 --- a/2023/lib/2023/8.ex +++ b/2023/lib/2023/8.ex @@ -5,20 +5,40 @@ aoc 2023, 8 do def p1(input) do {instructions, mappings} = read_input(input) - start = "AAA" - finish = "ZZZ" - all_but_last_step = instructions |> Stream.cycle() - |> Stream.scan(start, &step(&1, &2, mappings)) - |> Stream.take_while(&(&1 != finish)) + |> Stream.scan("AAA", &step(&1, &2, mappings)) + |> Stream.take_while(&(&1 != "ZZZ")) |> Enum.count() all_but_last_step + 1 end - def p2(_input) do + def p2(input) do + {instructions, mappings} = read_input(input) + + starts = + mappings + |> Map.keys() + |> Enum.filter(&String.ends_with?(&1, "A")) + + lengths = + starts + |> Enum.map(fn start -> + n = + instructions + |> Stream.cycle() + |> Stream.scan(start, &step(&1, &2, mappings)) + |> Stream.take_while(&(not String.ends_with?(&1, "Z"))) + |> Enum.count() + + n + 1 + end) + + Enum.reduce(lengths, fn a, b -> + div(a * b, Integer.gcd(a, b)) + end) end def step("L", curr, mappings) do @@ -33,6 +53,10 @@ aoc 2023, 8 do |> elem(1) end + def step_all(inst, currs, mappings) do + Enum.map(currs, &step(inst, &1, mappings)) + end + def read_input(input) do [instructions_string, _ | mapping_lines] = lines(input) instructions = letters(instructions_string) diff --git a/README.md b/README.md index ed36e90..d5cc989 100644 --- a/README.md +++ b/README.md @@ -14,7 +14,7 @@ 1. [2020] **17/50** 🌟 1. [2021] **43/50** 🌟 1. [2022] **14/50** 🌟 -1. [2023] **12/50** 🌟 +1. [2023] **13/50** 🌟 [2015]: ./2015 [2017]: ./2017