Day 9: Mirage Maintenance
Part one
sample_input =
"""
0 3 6 9 12 15
1 3 6 10 15 21
10 13 16 21 30 45
"""
defmodule MirageMaintenance do
def sum_extrapolated_values(report, mode \\ :forward) when mode in ~w(forward backward)a do
report
|> parse_report()
|> Enum.map(fn report -> extrapolate(report, mode) end)
|> Enum.sum()
end
defp parse_report(report) do
report
|> String.split("\n", trim: true)
|> Enum.map(fn line ->
String.split(line, " ", trim: true) |> Enum.map(&String.to_integer/1)
end)
end
defp extrapolate(numbers, mode) do
case mode do
:forward -> [Enum.reverse(numbers)]
:backward -> [numbers]
end
|> build_rows()
|> extrapolate_rows()
end
defp extrapolate_rows(rows), do: rows |> Enum.map(&hd/1) |> Enum.sum()
defp build_rows([last_row | _] = rows) do
if Enum.all?(last_row, &(&1 == 0)) do
rows
else
new_row =
last_row
|> Enum.chunk_every(2, 1, :discard)
|> Enum.map(fn [a, b] -> a - b end)
[new_row | rows]
|> build_rows()
end
end
end
MirageMaintenance.sum_extrapolated_values(sample_input)
# expected 114
Path.join(__DIR__, "day-9.input")
|> File.read!()
|> MirageMaintenance.sum_extrapolated_values()
# 1853145119
Part two
MirageMaintenance.sum_extrapolated_values(sample_input, :backward)
# expected 2
Path.join(__DIR__, "day-9.input")
|> File.read!()
|> MirageMaintenance.sum_extrapolated_values(:backward)
# 923