Formatting & Cleanup Doublelinked
This commit is contained in:
parent
72c4607879
commit
391e4bbc8d
3 changed files with 103 additions and 70 deletions
84
day4.exs
84
day4.exs
|
@ -1,96 +1,134 @@
|
||||||
defmodule DayFour do
|
defmodule DayFour do
|
||||||
|
|
||||||
def decode_all(input) do
|
def decode_all(input) do
|
||||||
partial = input
|
partial =
|
||||||
|
input
|
||||||
|> String.split("\n")
|
|> String.split("\n")
|
||||||
|> Enum.filter(&(&1 != ""))
|
|> Enum.filter(&(&1 != ""))
|
||||||
|> Enum.map(&DayFour.decode_log/1)
|
|> Enum.map(&DayFour.decode_log/1)
|
||||||
|> Enum.sort_by(fn {_,_, year, month, day, hour, minute} -> year * 100000000 + month * 100000 + day * 10000 + hour * 100 + minute end)
|
|> Enum.sort_by(fn {_, _, year, month, day, hour, minute} ->
|
||||||
|
year * 100_000_000 + month * 100_000 + day * 10000 + hour * 100 + minute
|
||||||
|
end)
|
||||||
|
|
||||||
DayFour.map_to_guard(partial, 0)
|
DayFour.map_to_guard(partial, 0)
|
||||||
# |> Enum.map(fn {action, guard, _, _, _, _, minute} -> {action, guard, minute} end)
|
# |> Enum.map(fn {action, guard, _, _, _, _, minute} -> {action, guard, minute} end)
|
||||||
end
|
end
|
||||||
|
|
||||||
def decode_log(log) do
|
def decode_log(log) do
|
||||||
pattern = ~r/\[(\d{4})-(\d{2})-(\d{2}) (\d{2}):(\d{2})\] (wakes|falls|Guard) #?(\d{0,})/
|
pattern = ~r/\[(\d{4})-(\d{2})-(\d{2}) (\d{2}):(\d{2})\] (wakes|falls|Guard) #?(\d{0,})/
|
||||||
[[ _ | match]] = Regex.scan(pattern, log)
|
[[_ | match]] = Regex.scan(pattern, log)
|
||||||
decode_entry(match)
|
decode_entry(match)
|
||||||
end
|
end
|
||||||
|
|
||||||
def decode_entry([year, month, day, hour, minute, "Guard", number]) do
|
def decode_entry([year, month, day, hour, minute, "Guard", number]) do
|
||||||
{:guard, String.to_integer(number), String.to_integer(year), String.to_integer(month), String.to_integer(day), String.to_integer(hour), String.to_integer(minute)}
|
{:guard, String.to_integer(number), String.to_integer(year), String.to_integer(month),
|
||||||
|
String.to_integer(day), String.to_integer(hour), String.to_integer(minute)}
|
||||||
end
|
end
|
||||||
|
|
||||||
def decode_entry([year, month, day, hour, minute, "wakes", _]) do
|
def decode_entry([year, month, day, hour, minute, "wakes", _]) do
|
||||||
{:wake, nil, String.to_integer(year), String.to_integer(month), String.to_integer(day), String.to_integer(hour), String.to_integer(minute)}
|
{:wake, nil, String.to_integer(year), String.to_integer(month), String.to_integer(day),
|
||||||
|
String.to_integer(hour), String.to_integer(minute)}
|
||||||
end
|
end
|
||||||
|
|
||||||
def decode_entry([year, month, day, hour, minute, "falls", _]) do
|
def decode_entry([year, month, day, hour, minute, "falls", _]) do
|
||||||
{:sleep, nil, String.to_integer(year), String.to_integer(month), String.to_integer(day), String.to_integer(hour), String.to_integer(minute)}
|
{:sleep, nil, String.to_integer(year), String.to_integer(month), String.to_integer(day),
|
||||||
|
String.to_integer(hour), String.to_integer(minute)}
|
||||||
end
|
end
|
||||||
|
|
||||||
def map_to_guard([{:guard, id, year, month, day, hour, minute} | tail], _) do
|
def map_to_guard([{:guard, id, year, month, day, hour, minute} | tail], _) do
|
||||||
now = {:guard, id, year, month, day, hour, minute}
|
now = {:guard, id, year, month, day, hour, minute}
|
||||||
[now | map_to_guard(tail, id)]
|
[now | map_to_guard(tail, id)]
|
||||||
end
|
end
|
||||||
|
|
||||||
def map_to_guard([now | tail], current) do
|
def map_to_guard([now | tail], current) do
|
||||||
{action, _, year, month, day, hour, minute} = now
|
{action, _, year, month, day, hour, minute} = now
|
||||||
[{action, current, year, month, day, hour, minute} | map_to_guard(tail, current)]
|
[{action, current, year, month, day, hour, minute} | map_to_guard(tail, current)]
|
||||||
end
|
end
|
||||||
|
|
||||||
def map_to_guard([], _), do: []
|
def map_to_guard([], _), do: []
|
||||||
|
|
||||||
def part_one(input) do
|
def part_one(input) do
|
||||||
minutes = Enum.zip(0..60, Enum.map(0..60, fn _ -> 0 end)) |> Map.new
|
minutes = Enum.zip(0..60, Enum.map(0..60, fn _ -> 0 end)) |> Map.new()
|
||||||
sleeping_by_guard = decode_all(input)
|
|
||||||
|
sleeping_by_guard =
|
||||||
|
decode_all(input)
|
||||||
|> Enum.group_by(fn {_, id, _, _, _, _, _} -> id end)
|
|> Enum.group_by(fn {_, id, _, _, _, _, _} -> id end)
|
||||||
|> Enum.map(fn {id, list} -> {id, Enum.sort_by(list, fn {_,_, year, month, day, hour, minute} -> year * 100000000 + month * 100000 + day * 10000 + hour * 100 + minute end)} end)
|
|> Enum.map(fn {id, list} ->
|
||||||
|
{id,
|
||||||
|
Enum.sort_by(list, fn {_, _, year, month, day, hour, minute} ->
|
||||||
|
year * 100_000_000 + month * 100_000 + day * 10000 + hour * 100 + minute
|
||||||
|
end)}
|
||||||
|
end)
|
||||||
|> Enum.map(fn {id, list} -> {id, calc_asleep_times(list, 60, minutes)} end)
|
|> Enum.map(fn {id, list} -> {id, calc_asleep_times(list, 60, minutes)} end)
|
||||||
time_by_guard = sleeping_by_guard
|
|
||||||
|
time_by_guard =
|
||||||
|
sleeping_by_guard
|
||||||
|> Enum.map(fn {id, times} -> {id, Map.to_list(times)} end)
|
|> Enum.map(fn {id, times} -> {id, Map.to_list(times)} end)
|
||||||
|> Enum.sort_by(fn {_, times} -> List.foldl(times, 0, fn {_, c}, acc -> c + acc end) end)
|
|> Enum.sort_by(fn {_, times} -> List.foldl(times, 0, fn {_, c}, acc -> c + acc end) end)
|
||||||
|> Enum.reverse
|
|> Enum.reverse()
|
||||||
|
|
||||||
[longest_sleeper | _] = time_by_guard
|
[longest_sleeper | _] = time_by_guard
|
||||||
{id, times} = longest_sleeper
|
{id, times} = longest_sleeper
|
||||||
minutes = times
|
|
||||||
|
minutes =
|
||||||
|
times
|
||||||
|> Enum.sort_by(fn {_, time} -> time end)
|
|> Enum.sort_by(fn {_, time} -> time end)
|
||||||
|> Enum.reverse
|
|> Enum.reverse()
|
||||||
[{longest_minute, _} | _ ] = minutes
|
|
||||||
|
[{longest_minute, _} | _] = minutes
|
||||||
"(id: #{id}, minute: #{longest_minute})"
|
"(id: #{id}, minute: #{longest_minute})"
|
||||||
end
|
end
|
||||||
|
|
||||||
def calc_asleep_times([{:guard, _, _, _, _, _, _} | tail], 60, acc) do
|
def calc_asleep_times([{:guard, _, _, _, _, _, _} | tail], 60, acc) do
|
||||||
calc_asleep_times(tail, 60, acc)
|
calc_asleep_times(tail, 60, acc)
|
||||||
end
|
end
|
||||||
|
|
||||||
def calc_asleep_times([{:guard, _, _, _, _, _, _} | tail], last, acc) do
|
def calc_asleep_times([{:guard, _, _, _, _, _, _} | tail], last, acc) do
|
||||||
times = Enum.to_list(last..60)
|
times = Enum.to_list(last..60)
|
||||||
calc_asleep_times(tail, 60, increment_map(times, acc))
|
calc_asleep_times(tail, 60, increment_map(times, acc))
|
||||||
end
|
end
|
||||||
|
|
||||||
def calc_asleep_times([{:sleep, _, _, _, _, _, minute} | tail], _, acc) do
|
def calc_asleep_times([{:sleep, _, _, _, _, _, minute} | tail], _, acc) do
|
||||||
calc_asleep_times(tail, minute, acc)
|
calc_asleep_times(tail, minute, acc)
|
||||||
end
|
end
|
||||||
|
|
||||||
def calc_asleep_times([{:wake, _, _, _, _, _, minute} | tail], last, acc) do
|
def calc_asleep_times([{:wake, _, _, _, _, _, minute} | tail], last, acc) do
|
||||||
times = Enum.to_list(last..minute)
|
times = Enum.to_list(last..minute)
|
||||||
calc_asleep_times(tail, 60, increment_map(times, acc))
|
calc_asleep_times(tail, 60, increment_map(times, acc))
|
||||||
end
|
end
|
||||||
|
|
||||||
def calc_asleep_times([], 60, acc), do: acc
|
def calc_asleep_times([], 60, acc), do: acc
|
||||||
def calc_asleep_times([], last, acc), do: increment_map(Enum.to_list(last..60), acc)
|
def calc_asleep_times([], last, acc), do: increment_map(Enum.to_list(last..60), acc)
|
||||||
|
|
||||||
def increment_map([head | tail], acc) do
|
def increment_map([head | tail], acc) do
|
||||||
increment_map(tail, Map.update!(acc, head, &( &1 + 1)))
|
increment_map(tail, Map.update!(acc, head, &(&1 + 1)))
|
||||||
end
|
end
|
||||||
|
|
||||||
def increment_map([], acc), do: acc
|
def increment_map([], acc), do: acc
|
||||||
|
|
||||||
def part_two(input) do
|
def part_two(input) do
|
||||||
minutes = Enum.zip(0..60, Enum.map(0..60, fn _ -> 0 end)) |> Map.new
|
minutes = Enum.zip(0..60, Enum.map(0..60, fn _ -> 0 end)) |> Map.new()
|
||||||
sleeping_by_guard = decode_all(input)
|
|
||||||
|
sleeping_by_guard =
|
||||||
|
decode_all(input)
|
||||||
|> Enum.group_by(fn {_, id, _, _, _, _, _} -> id end)
|
|> Enum.group_by(fn {_, id, _, _, _, _, _} -> id end)
|
||||||
|> Enum.map(fn {id, list} -> {id, Enum.sort_by(list, fn {_,_, year, month, day, hour, minute} -> year * 100000000 + month * 100000 + day * 10000 + hour * 100 + minute end)} end)
|
|> Enum.map(fn {id, list} ->
|
||||||
|
{id,
|
||||||
|
Enum.sort_by(list, fn {_, _, year, month, day, hour, minute} ->
|
||||||
|
year * 100_000_000 + month * 100_000 + day * 10000 + hour * 100 + minute
|
||||||
|
end)}
|
||||||
|
end)
|
||||||
|> Enum.map(fn {id, list} -> {id, calc_asleep_times(list, 60, minutes)} end)
|
|> Enum.map(fn {id, list} -> {id, calc_asleep_times(list, 60, minutes)} end)
|
||||||
{id, {minute, time}} = sleeping_by_guard
|
|
||||||
|
{id, {minute, time}} =
|
||||||
|
sleeping_by_guard
|
||||||
|> Enum.map(fn {id, sleeps} -> {id, Enum.max_by(sleeps, fn {minute, time} -> time end)} end)
|
|> Enum.map(fn {id, sleeps} -> {id, Enum.max_by(sleeps, fn {minute, time} -> time end)} end)
|
||||||
|> Enum.max_by(fn {id, {minute, time}} -> time end)
|
|> Enum.max_by(fn {id, {minute, time}} -> time end)
|
||||||
|
|
||||||
"id: #{id} minute: #{minute} times: #{time}"
|
"id: #{id} minute: #{minute} times: #{time}"
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
{:ok, content} = File.read "input4.txt"
|
{:ok, content} = File.read("input4.txt")
|
||||||
|
|
||||||
IO.puts "Part 1: #{DayFour.part_one(content)}"
|
IO.puts("Part 1: #{DayFour.part_one(content)}")
|
||||||
IO.puts "Part 2: #{DayFour.part_two(content)}"
|
IO.puts("Part 2: #{DayFour.part_two(content)}")
|
||||||
|
|
33
day5.exs
33
day5.exs
|
@ -2,15 +2,16 @@ defmodule DayFive do
|
||||||
def part_one(input) do
|
def part_one(input) do
|
||||||
shortened = fully_react_new(input)
|
shortened = fully_react_new(input)
|
||||||
# IO.puts shortened
|
# IO.puts shortened
|
||||||
(String.length shortened) - 1
|
String.length(shortened) - 1
|
||||||
end
|
end
|
||||||
|
|
||||||
def fully_react(input) do
|
def fully_react(input) do
|
||||||
replacer = ~r/Aa|Bb|Cc|Dd|Ee|Ff|Gg|Hh|Ii|Jj|Kk|Ll|Mm|Nn|Oo|Pp|Qq|Rr|Ss|Tt|Uu|Ww|Vv|Xx|Yy|Zz|aA|bB|cC|dD|eE|fF|gG|hH|iI|jJ|kK|lL|mM|nN|oO|pP|qQ|rR|sS|tT|uU|wW|vV|xX|yY|zZ/
|
replacer =
|
||||||
|
~r/Aa|Bb|Cc|Dd|Ee|Ff|Gg|Hh|Ii|Jj|Kk|Ll|Mm|Nn|Oo|Pp|Qq|Rr|Ss|Tt|Uu|Ww|Vv|Xx|Yy|Zz|aA|bB|cC|dD|eE|fF|gG|hH|iI|jJ|kK|lL|mM|nN|oO|pP|qQ|rR|sS|tT|uU|wW|vV|xX|yY|zZ/
|
||||||
|
|
||||||
replace_forever(input, replacer, "")
|
replace_forever(input, replacer, "")
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
def replace_forever(string, pattern, replacement) do
|
def replace_forever(string, pattern, replacement) do
|
||||||
if Regex.match?(pattern, string) do
|
if Regex.match?(pattern, string) do
|
||||||
replace_forever(Regex.replace(pattern, string, replacement), pattern, replacement)
|
replace_forever(Regex.replace(pattern, string, replacement), pattern, replacement)
|
||||||
|
@ -19,34 +20,40 @@ defmodule DayFive do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def react([<< char1 >> , << char2 >> | tail]) when char1 == char2 - 32 or char2 == char1 - 32, do: react(tail)
|
def react([<<char1>>, <<char2>> | tail]) when char1 == char2 - 32 or char2 == char1 - 32,
|
||||||
|
do: react(tail)
|
||||||
|
|
||||||
def react([char | tail]), do: [char | react(tail)]
|
def react([char | tail]), do: [char | react(tail)]
|
||||||
def react(""), do: []
|
def react(""), do: []
|
||||||
def react([]), do: []
|
def react([]), do: []
|
||||||
|
|
||||||
def fully_react_new(input) do
|
def fully_react_new(input) do
|
||||||
# IO.puts "mark"
|
# IO.puts "mark"
|
||||||
Enum.join( fully_react_new(String.codepoints(input), []) )
|
Enum.join(fully_react_new(String.codepoints(input), []))
|
||||||
end
|
end
|
||||||
|
|
||||||
def fully_react_new(input, acc) when input == acc, do: acc
|
def fully_react_new(input, acc) when input == acc, do: acc
|
||||||
|
|
||||||
def fully_react_new(input, _acc) do
|
def fully_react_new(input, _acc) do
|
||||||
# IO.puts("#{length _acc} #{length input}")
|
# IO.puts("#{length _acc} #{length input}")
|
||||||
fully_react_new(react(input), input)
|
fully_react_new(react(input), input)
|
||||||
end
|
end
|
||||||
|
|
||||||
def part_two(input) do
|
def part_two(input) do
|
||||||
chars = Enum.map(?a..?z, &(<< &1 >>))
|
chars = Enum.map(?a..?z, &<<&1>>)
|
||||||
[{_char, poly} | _ ] = Enum.map(chars, fn char -> {char, String.replace(input, char, "")} end)
|
|
||||||
|> Enum.map(fn {char, poly} -> {char, String.replace(poly, String.upcase(char), "") } end)
|
[{_char, poly} | _] =
|
||||||
|> Enum.map(fn {char, poly} -> {char, fully_react_new(poly)} end)
|
Enum.map(chars, fn char -> {char, String.replace(input, char, "")} end)
|
||||||
|> Enum.sort_by(fn {_char, poly} -> String.length(poly) end)
|
|> Enum.map(fn {char, poly} -> {char, String.replace(poly, String.upcase(char), "")} end)
|
||||||
|
|> Enum.map(fn {char, poly} -> {char, fully_react_new(poly)} end)
|
||||||
|
|> Enum.sort_by(fn {_char, poly} -> String.length(poly) end)
|
||||||
|
|
||||||
# IO.puts poly
|
# IO.puts poly
|
||||||
String.length(poly) - 1
|
String.length(poly) - 1
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
{:ok, content} = File.read "input5.txt"
|
{:ok, content} = File.read("input5.txt")
|
||||||
|
|
||||||
IO.puts "Part 1: #{DayFive.part_one(content)}"
|
IO.puts("Part 1: #{DayFive.part_one(content)}")
|
||||||
IO.puts "Part 2: #{DayFive.part_two(content)}"
|
IO.puts("Part 2: #{DayFive.part_two(content)}")
|
||||||
|
|
|
@ -2,25 +2,29 @@ defmodule DayFive do
|
||||||
def part_one(input) do
|
def part_one(input) do
|
||||||
shortened = fully_react_new(input)
|
shortened = fully_react_new(input)
|
||||||
# IO.puts shortened
|
# IO.puts shortened
|
||||||
(String.length shortened) - 1
|
String.length(shortened) - 1
|
||||||
end
|
end
|
||||||
|
|
||||||
def fully_react(input) do
|
def part_two(input) do
|
||||||
replacer = ~r/Aa|Bb|Cc|Dd|Ee|Ff|Gg|Hh|Ii|Jj|Kk|Ll|Mm|Nn|Oo|Pp|Qq|Rr|Ss|Tt|Uu|Ww|Vv|Xx|Yy|Zz|aA|bB|cC|dD|eE|fF|gG|hH|iI|jJ|kK|lL|mM|nN|oO|pP|qQ|rR|sS|tT|uU|wW|vV|xX|yY|zZ/
|
chars = Enum.map(?a..?z, &<<&1>>)
|
||||||
replace_forever(input, replacer, "")
|
|
||||||
|
[{_char, poly} | _] =
|
||||||
|
Enum.map(chars, fn char -> {char, String.replace(input, char, "")} end)
|
||||||
|
|> Enum.map(fn {char, poly} -> {char, String.replace(poly, String.upcase(char), "")} end)
|
||||||
|
|> Enum.map(fn {char, poly} -> {char, fully_react_new(poly)} end)
|
||||||
|
|> Enum.sort_by(fn {_char, poly} -> String.length(poly) end)
|
||||||
|
|
||||||
|
# IO.puts poly
|
||||||
|
String.length(poly) - 1
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def react([<<char1>>, <<char2>> | tail], rev) when char1 == char2 - 32 or char2 == char1 - 32,
|
||||||
|
do: react(tail, rev)
|
||||||
|
|
||||||
def replace_forever(string, pattern, replacement) do
|
def react([<<char1>> | tail], [<<char2>> | rev])
|
||||||
if Regex.match?(pattern, string) do
|
when char1 == char2 - 32 or char2 == char1 - 32,
|
||||||
replace_forever(Regex.replace(pattern, string, replacement), pattern, replacement)
|
do: react(tail, rev)
|
||||||
else
|
|
||||||
string
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
def react([<< char1 >> , << char2 >> | tail], rev) when char1 == char2 - 32 or char2 == char1 - 32, do: react(tail, rev)
|
|
||||||
def react([<< char1 >> | tail], [<< char2 >> | rev]) when char1 == char2 - 32 or char2 == char1 - 32, do: react(tail, rev)
|
|
||||||
def react([char | tail], rev), do: react(tail, [char | rev])
|
def react([char | tail], rev), do: react(tail, [char | rev])
|
||||||
def react("", rev), do: rev
|
def react("", rev), do: rev
|
||||||
def react([], rev), do: rev
|
def react([], rev), do: rev
|
||||||
|
@ -29,25 +33,9 @@ defmodule DayFive do
|
||||||
# IO.puts "mark"
|
# IO.puts "mark"
|
||||||
String.reverse(Enum.join(react(String.codepoints(input), [])))
|
String.reverse(Enum.join(react(String.codepoints(input), [])))
|
||||||
end
|
end
|
||||||
|
|
||||||
#def fully_react_new(input, acc) when input == acc, do: acc
|
|
||||||
#def fully_react_new(input, _acc) do
|
|
||||||
# IO.puts("#{length _acc} #{length input}")
|
|
||||||
# fully_react_new(react(input), input)
|
|
||||||
#end
|
|
||||||
|
|
||||||
def part_two(input) do
|
|
||||||
chars = Enum.map(?a..?z, &(<< &1 >>))
|
|
||||||
[{_char, poly} | _ ] = Enum.map(chars, fn char -> {char, String.replace(input, char, "")} end)
|
|
||||||
|> Enum.map(fn {char, poly} -> {char, String.replace(poly, String.upcase(char), "") } end)
|
|
||||||
|> Enum.map(fn {char, poly} -> {char, fully_react_new(poly)} end)
|
|
||||||
|> Enum.sort_by(fn {_char, poly} -> String.length(poly) end)
|
|
||||||
# IO.puts poly
|
|
||||||
String.length(poly) - 1
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
|
|
||||||
{:ok, content} = File.read "input5.txt"
|
{:ok, content} = File.read("input5.txt")
|
||||||
|
|
||||||
IO.puts "Part 1: #{DayFive.part_one(content)}"
|
IO.puts("Part 1: #{DayFive.part_one(content)}")
|
||||||
IO.puts "Part 2: #{DayFive.part_two(content)}"
|
IO.puts("Part 2: #{DayFive.part_two(content)}")
|
||||||
|
|
Loading…
Reference in a new issue