forked from matelaszlo/advent-of-code-scala
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathDay14.scala
42 lines (31 loc) · 1.38 KB
/
Day14.scala
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
package com.lmat.adventofcode.year2018
import com.lmat.adventofcode.SimpleCommonPuzzle
import com.lmat.util.Files.readResource
import scala.util.Try
object Day14 extends SimpleCommonPuzzle[Int, String, Int] {
override def parse(resource: String): Int = readResource(resource).headOption.flatMap(row => Try(row.toInt).toOption).get
/**
* If we can generate an infinite Stream of the recipes both parts become trivial
*/
def recipeStream: LazyList[Int] = {
type State = (Vector[Int], Int, Int)
def next(state: State): State = {
val (recipes, i1, i2) = state
val recipe1 = recipes(i1)
val recipe2 = recipes(i2)
val extendedRecipes = recipes ++ toDigits(recipe1 + recipe2)
(extendedRecipes, shiftRight(i1, recipe1 + 1, extendedRecipes.length), shiftRight(i2, recipe2 + 1, extendedRecipes.length))
}
LazyList.iterate((Vector(3, 7), 0, 1))(next).zipWithIndex.map { case ((recipes, _, _), index) => recipes(index) }
}
def toDigits(number: Int): Vector[Int] =
number.toString.toCharArray.map(_.asDigit).toVector
def shiftRight(i: Int, n: Int, length: Int): Int = {
val shifted = i + n
if(shifted < length) shifted else shifted % length
}
override def part1(number: Int): String =
recipeStream.slice(number, number + 10).mkString
override def part2(number: Int): Int =
recipeStream.indexOfSlice(toDigits(number))
}