package tf.bug.aoc.y2020 import cats.effect._ import cats.syntax.all._ import fs2._ import scala.collection.SortedSet import tf.bug.aoc.Day object Day5 extends Day { override def part1[F[_]: Async]: Pipe[F, String, String] = (lines: Stream[F, String]) => { lines.through(seats[F]) .fold1(_.max(_)) .map(_.show) } case class SearchState(min: Int, max: Int, sum: Int) override def part2[F[_]: Async]: Pipe[F, String, String] = (lines: Stream[F, String]) => { lines .filter(_.nonEmpty) .through(seats[F]) .fold(SearchState(Int.MaxValue, Int.MinValue, 0)) { case (SearchState(min, max, sum), seat) => val newMin = seat.min(min) val newMax = seat.max(max) val newSum = sum + seat SearchState(newMin, newMax, newSum) } .map { case SearchState(min, max, sum) => val range = (max - min) + 1 val total = ((max + min) * range) / 2 total - sum } .map(_.show) } def seats[F[_]: Async]: Pipe[F, String, Int] = _.map(_.foldLeft(0) { case (id, ch) => val newBit = ((ch & 4) >>> 2) ^ 1 (id * 2) + newBit }) }