Advent of Code Day 13
Mix.install([
:kino,
:jason
])
Input
raw_input = Kino.Input.textarea("Please paste your input here")
input = Kino.Input.read(raw_input)
Order Module
defmodule Ordering do
def order([], []), do: nil
def order([_ | _], []), do: false
def order([], [_ | _]), do: true
def order([x | x_rest], [y | y_rest]) when is_integer(x) and is_integer(y),
do: (x == y && order(x_rest, y_rest)) || x < y
def order([x | x_rest], [y | y_rest]) when is_list(x) and is_list(y) do
case(order(x, y)) do
nil -> order(x_rest, y_rest)
val -> val
end
end
def order([x | x_rest], [y | y_rest]) when is_list(x) and is_integer(y),
do: order([x | x_rest], [[y] | y_rest])
def order([x | x_rest], [y | y_rest]) when is_integer(x) and is_list(y),
do: order([[x] | x_rest], [y | y_rest])
end
Part 1
input
|> String.split("\n\n")
|> Enum.map(fn pair ->
[a, b] = String.split(pair, "\n")
{Jason.decode!(a), Jason.decode!(b)}
end)
|> Enum.with_index(1)
|> Enum.filter(fn {{x, y}, _} -> Ordering.order(x, y) end)
|> Enum.map(&elem(&1, 1))
|> Enum.sum()
Part 2
input
|> String.split("\n\n")
|> Enum.flat_map(&String.split(&1, "\n"))
|> Enum.map(&Jason.decode!/1)
|> Kernel.++([[[2]], [[6]]])
|> Enum.sort_by(&Function.identity/1, &Ordering.order/2)
|> Enum.with_index(1)
|> Enum.filter(fn {elem, _} -> elem in [[[2]], [[6]]] end)
|> Enum.map(&elem(&1, 1))
|> Enum.product()