Skip to content

Instantly share code, notes, and snippets.

@sasa1977
Created December 6, 2019 09:05
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save sasa1977/0e48a26ff95b31f5954f5f6fb3d5a4fc to your computer and use it in GitHub Desktop.
Save sasa1977/0e48a26ff95b31f5954f5f6fb3d5a4fc to your computer and use it in GitHub Desktop.
defmodule Aoc201906 do
def run do
IO.inspect(part1())
IO.inspect(part2())
end
defp part1(), do: total_number_of_orbits(universe())
defp total_number_of_orbits(universe, center \\ "COM", distance \\ 0) do
orbiters = orbiters(universe, center)
distance +
(orbiters
|> Stream.map(&total_number_of_orbits(universe, &1, distance + 1))
|> Enum.sum())
end
defp part2() do
universe = universe()
my_path_to_com = MapSet.new(path_to_com(universe, "YOU"))
santas_path_to_com = MapSet.new(path_to_com(universe, "SAN"))
common_path = MapSet.intersection(my_path_to_com, santas_path_to_com)
MapSet.size(my_path_to_com) + MapSet.size(santas_path_to_com) - 2 * MapSet.size(common_path)
end
defp path_to_com(universe, object) do
object
|> Stream.iterate(&center(universe, &1))
|> Stream.drop(1)
|> Enum.take_while(&(not is_nil(&1)))
end
defp empty_universe(), do: %{}
defp add_object(universe, object), do: Map.put_new(universe, object, %{orbiters: [], center: nil})
defp center(universe, object), do: Map.fetch!(universe, object).center
defp orbiters(universe, center), do: Map.fetch!(universe, center).orbiters
defp add_orbit(universe, center, object) do
universe
|> add_object(center)
|> add_object(object)
|> update_in([center, :orbiters], &[object | &1])
|> put_in([object, :center], center)
end
defp universe() do
Aoc.input_lines(2019, 06)
|> Stream.map(&String.split(&1, ")"))
|> Enum.reduce(empty_universe(), fn [center, object], universe -> add_orbit(universe, center, object) end)
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment