Day 25
# Note: when making the next template, something like this works well:
# `cat day04.livemd | sed 's/25/04/' > day04.livemd`
# When inspecting lists of numbers, use "charlists: :as_lists"
#
Mix.install([
# Join the string so a copy of dayN to dayM doesn't destroy it.
{:kino, "~> 0.1" <> "4.2"}
])
# Join the string so a copy of dayN to dayM doesn't destroy it.
IEx.Helpers.c("/Users/johnb/dev/2" <> "0" <> "2" <> "4adventOfCode/advent_of_code.ex")
alias AdventOfCode, as: AOC
alias Kino.Input
Installation and Data
input_example = Kino.Input.textarea("Example Data", monospace: true)
input_puzzleInput = Kino.Input.textarea("Puzzle Input", monospace: true)
input_source_select =
Kino.Input.select("Source", [{:example, "example"}, {:puzzle_input, "puzzle input"}])
data = fn ->
(Kino.Input.read(input_source_select) == :example &&
Kino.Input.read(input_example)) ||
Kino.Input.read(input_puzzleInput)
end
Solution
defmodule Day25 do
@empty "."
@filled "#"
def line_empty?(grid, cells) do
Enum.all?(cells, fn cell -> grid[cell] == @empty end)
end
def top_line_empty?(grid), do: line_empty?(grid, 0..(grid.grid_width - 1))
def bottom_line_empty?(grid) do
line_empty?(grid, (grid.last_cell - grid.grid_width + 1)..grid.last_cell)
end
def parse(text) do
grids = text
|> AOC.as_doublespaced_paragraphs()
|> Enum.map(fn paragraph -> AOC.as_grid(paragraph) end)
keys = Enum.filter(grids, fn grid -> top_line_empty?(grid) end)
locks = Enum.filter(grids, fn grid -> bottom_line_empty?(grid) end)
[keys, locks]
end
def solve1(text) do
[keys, locks] = parse(text)
keys
|> Enum.reduce(0, fn key, acc ->
locks
|> Enum.reduce(acc, fn lock, acc1 ->
if lock.grid_height == key.grid_height &&
lock.grid_width == key.grid_width &&
Enum.all?(AOC.grid_cells(lock), fn cell ->
lock[cell] != @filled || key[cell] != @filled
end) do
acc1 + 1
else
acc1
end
end)
end)
end
def solve2(_text) do
# There is no real part 2 - just a free star if/when you've solved all the others.
end
end
# Example:
IO.inspect(Time.utc_now())
data.()
|> Day25.solve1()
|> IO.inspect(label: "\n*** Part 1 solution (example: 3)")
IO.inspect(Time.utc_now())
#
# IO.inspect(Time.utc_now())
# data.()
# |> Day25.solve2()
# |> IO.inspect(label: "\n*** Part 2 solution (example: )")
# IO.inspect(Time.utc_now())
#