Skip to content

Commit

Permalink
2024 Day 04 Part 1 & 2
Browse files Browse the repository at this point in the history
  • Loading branch information
fmmr committed Dec 4, 2024
1 parent 3908087 commit ea79ab2
Show file tree
Hide file tree
Showing 6 changed files with 163 additions and 4 deletions.
12 changes: 12 additions & 0 deletions src/main/kotlin/no/rodland/advent/Dir.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
package no.rodland.advent

enum class Dir(val move: (input: Pos, howMuch: Int) -> Pos) {
N({ pos, howMuch -> pos.above(howMuch) }),
S({ pos, howMuch -> pos.below(howMuch) }),
W({ pos, howMuch -> pos.left(howMuch) }),
E({ pos, howMuch -> pos.right(howMuch) }),
NW({ pos, howMuch -> pos.nw(howMuch) }),
NE({ pos, howMuch -> pos.ne(howMuch) }),
SW({ pos, howMuch -> pos.sw(howMuch) }),
SE({ pos, howMuch -> pos.se(howMuch) }),
}
8 changes: 4 additions & 4 deletions src/main/kotlin/no/rodland/advent/SpacePos.kt
Original file line number Diff line number Diff line change
Expand Up @@ -173,10 +173,10 @@ data class Pos(val x: Int, val y: Int) : SpacePos(), Comparable<Pos> {
fun below(howMuch: Int = 1): Pos = Pos(x, y + howMuch)
fun left(howMuch: Int = 1): Pos = Pos(x - howMuch, y)
fun right(howMuch: Int = 1): Pos = Pos(x + howMuch, y)
private fun nw(): Pos = Pos(x - 1, y - 1)
fun ne(): Pos = Pos(x + 1, y - 1)
fun sw(): Pos = Pos(x - 1, y + 1)
fun se(): Pos = Pos(x + 1, y + 1)
fun nw(howMuch: Int = 1): Pos = Pos(x - howMuch, y - howMuch)
fun ne(howMuch: Int = 1): Pos = Pos(x + howMuch, y - howMuch)
fun sw(howMuch: Int = 1): Pos = Pos(x - howMuch, y + howMuch)
fun se(howMuch: Int = 1): Pos = Pos(x + howMuch, y + howMuch)

private fun Any?.size(): Int {
return when (this) {
Expand Down
52 changes: 52 additions & 0 deletions src/main/kotlin/no/rodland/advent_2024/Day04.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
package no.rodland.advent_2024

import no.rodland.advent.Day
import no.rodland.advent.Dir
import no.rodland.advent.Pos

// template generated: 04/12/2024
// Fredrik Rødland 2024
typealias Grid = Array<CharArray>

class Day04(val input: List<String>) : Day<Int, Int, Grid> {

private val parsed = input.parse()

override fun partOne(): Int {
return parsed.mapIndexed { y, row ->
row.mapIndexed { x, _ ->
val start = Pos(x, y)
val words = Dir.entries.map { d ->
(0..3)
.map { num -> d.move(start, num) }
.filter { p -> p.isInGrid(parsed) }
.map { p -> parsed[p.y][p.x] }
.joinToString("")
}.count { it == "XMAS" }
words
}.sum()
}.sum()
}

override fun partTwo(): Int {
val intRange = 1..(parsed.size - 2) // assuming grid is square (which both example and input is), avoiding both a filter and many comparisons.
return intRange.sumOf { y ->
intRange.map { x ->
val start = Pos(x, y)
listOf(listOf(start.nw(), start, start.se()), listOf(start.sw(), start, start.ne()))
.all { diagonal ->
diagonal.map { p -> parsed[p.y][p.x] }.joinToString("").let { it == "MAS" || it == "SAM" }
}
}.count { it }
}
}

override fun List<String>.parse(): Grid {
return indices.map { y -> indices.map { x -> this[y][x] }.toCharArray() }.toTypedArray()
}

override val day = "04".toInt()
}



1 change: 1 addition & 0 deletions src/main/script/download_aoc_input.sh
Original file line number Diff line number Diff line change
Expand Up @@ -26,3 +26,4 @@ tail -10 "$PUZZLE_FILE"
echo
echo "TEST-FILE: $PUZZLE_FILE_TEST"
echo "FILE: $PUZZLE_FILE"
echo "NUM-LINES: " `wc -l $PUZZLE_FILE`
84 changes: 84 additions & 0 deletions src/test/kotlin/no/rodland/advent_2024/Day04Test.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
package no.rodland.advent_2024

import no.rodland.advent.*
import org.junit.jupiter.api.Nested
import org.junit.jupiter.api.Test
import readFile

//
// run: download_aoc_input.sh to download input
//

@Suppress("ClassName")
@DisableSlow
internal class Day04Test {
private val data04 = "2024/input_04.txt".readFile()
private val test04 = "2024/input_04_test.txt".readFile()

private val resultTestOne = 18
private val resultTestTwo = 9
private val resultOne = 2344
private val resultTwo = 1815

val test = defaultTestSuiteParseOnInit(
Day04(data04),
Day04(test04),
resultTestOne,
resultOne,
resultTestTwo,
resultTwo,
{ Day04(data04) },
{ Day04(test04) },
numTestPart1 = 1,
numTestPart2 = 1
)

@Nested
inner class Init {
@Test
fun `04,-,example,1`() {
report(AOCTest({ "123".toInt() }, Unit, 123, 5, "04".toInt(), Part.TWO, false, "example"))
}

@Test
fun `04,-,example,2`() {
report(test.initTest.copy())
}

@Test
fun `04,-,test,init`() {
report(test.initTest)
}

@Test
fun `04,-,live,init`() {
report(test.initLive)
}
}

@Nested
inner class `Part 1` {
@Test
fun `04,1,test`() {
report(test.testPart1)
}

@Test
fun `04,1,live,1`() {
report(test.livePart1)
}
}

@Nested
inner class `Part 2` {
@Test
fun `04,2,test`() {
report(test.testPart2)
}

@Test
fun `04,2,live,1`() {
report(test.livePart2)
}
}
}
10 changes: 10 additions & 0 deletions src/test/resources/2024/input_04_test.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
MMMSXXMASM
MSAMXMSMSA
AMXSXMAAMM
MSAMASMSMX
XMASAMXAMM
XXAMMXXAMA
SMSMSASXSS
SAXAMASAAA
MAMMMXMMMM
MXMXAXMASX

0 comments on commit ea79ab2

Please sign in to comment.