🎄 Year 2022 🔔 Day 05
Parse input
filename = "#{__DIR__}/../../../inputs/2022/day05.txt"
[stack_input, [""], step_input] =
File.stream!(filename)
|> Enum.map(&String.trim(&1, "\n"))
|> Enum.chunk_by(&(&1 == ""))
stacks =
stack_input
|> Enum.reverse()
|> Enum.drop(1)
|> Enum.map(&String.graphemes/1)
|> Enum.map(&Enum.chunk_every(&1, 3, 4, :discard))
|> Enum.map(&Enum.map(&1, fn [_, char, _] -> char end))
|> then(fn rows ->
rows |> List.zip() |> Enum.map(&Tuple.to_list/1) |> Enum.map(&Enum.reverse/1)
end)
|> Enum.map(&Enum.filter(&1, fn e -> e != " " end))
steps =
step_input
|> Enum.map(&String.split(&1, " "))
|> Enum.map(&Enum.drop_every(&1, 2))
|> Enum.map(&Enum.map(&1, fn e -> String.to_integer(e) end))
Part One
steps
|> Enum.reduce(stacks, fn [count, from, to], stacks ->
to_add = Enum.at(stacks, from - 1) |> Enum.take(count) |> Enum.reverse()
stacks
|> List.update_at(from - 1, &Enum.drop(&1, count))
|> List.update_at(to - 1, &Enum.concat(to_add, &1))
end)
|> Enum.map(&List.first/1)
|> Enum.join()
Part two
steps
|> Enum.reduce(stacks, fn [count, from, to], stacks ->
to_add = Enum.at(stacks, from - 1) |> Enum.take(count)
stacks
|> List.update_at(from - 1, &Enum.drop(&1, count))
|> List.update_at(to - 1, &Enum.concat(to_add, &1))
end)
|> Enum.map(&List.first/1)
|> Enum.join()