Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit 6fc2555

Browse files
committed
Merge branch 'feature/day18' into develop
2 parents 27a6ea8 + 2816045 commit 6fc2555

File tree

1 file changed

+102
-0
lines changed
  • year2024/src/main/kotlin/net/olegg/aoc/year2024/day18

1 file changed

+102
-0
lines changed
Lines changed: 102 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,102 @@
1+
package net.olegg.aoc.year2024.day18
2+
3+
import net.olegg.aoc.someday.SomeDay
4+
import net.olegg.aoc.utils.Directions.Companion.NEXT_4
5+
import net.olegg.aoc.utils.Vector2D
6+
import net.olegg.aoc.utils.parseInts
7+
import net.olegg.aoc.utils.get
8+
import net.olegg.aoc.utils.set
9+
import net.olegg.aoc.year2024.DayOf2024
10+
11+
/**
12+
* See [Year 2024, Day 18](https://adventofcode.com/2024/day/18)
13+
*/
14+
object Day18 : DayOf2024(18) {
15+
private val size = 71
16+
17+
override fun first(): Any? {
18+
val bytes = lines.map { line ->
19+
val (x, y) = line.parseInts(",")
20+
Vector2D(x, y)
21+
}.take(1024).toSet()
22+
23+
val map = List(size) { y -> List(size) { x -> Vector2D(x, y) in bytes } }
24+
25+
val start = Vector2D(0, 0) to 0
26+
val finish = Vector2D(size - 1, size - 1)
27+
val queue = ArrayDeque(listOf(start))
28+
val seen = mutableSetOf<Pair<Vector2D, Int>>()
29+
30+
while (queue.isNotEmpty()) {
31+
val curr = queue.removeFirst()
32+
val (point, step) = curr
33+
if (point == finish) {
34+
return step
35+
}
36+
if (curr in seen) {
37+
continue
38+
}
39+
seen += curr
40+
41+
queue += NEXT_4.map { point + it.step }
42+
.filter { map[it] == false }
43+
.map { it to step + 1 }
44+
}
45+
46+
return -1
47+
}
48+
49+
override fun second(): Any? {
50+
val bytes = lines.map { line ->
51+
val (x, y) = line.parseInts(",")
52+
Vector2D(x, y)
53+
}
54+
55+
var left = 0
56+
var right = bytes.lastIndex
57+
var mid = (left + right) / 2
58+
59+
while (right - left > 1) {
60+
val cut = bytes.take(mid).toSet()
61+
val map = List(size) { y -> MutableList(size) { x -> Vector2D(x, y) in cut } }
62+
63+
if (fill(map)) {
64+
left = mid
65+
} else {
66+
right = mid
67+
}
68+
mid = (left + right) / 2
69+
}
70+
71+
return bytes[left].let { "${it.x},${it.y}" }
72+
}
73+
74+
private fun fill(map: List<MutableList<Boolean>>): Boolean {
75+
val start = Vector2D(0, 0)
76+
val finish = Vector2D(size - 1, size - 1)
77+
val queue = ArrayDeque(listOf(start))
78+
val seen = mutableSetOf<Vector2D>()
79+
80+
while (queue.isNotEmpty()) {
81+
val curr = queue.removeFirst()
82+
if (curr == finish) {
83+
return true
84+
}
85+
if (curr in seen) {
86+
continue
87+
}
88+
seen += curr
89+
90+
val next = NEXT_4.map { curr + it.step }
91+
.filter { map[it] == false }
92+
93+
next.forEach { map[it] = true }
94+
95+
queue += next
96+
}
97+
98+
return map[finish]!!
99+
}
100+
}
101+
102+
fun main() = SomeDay.mainify(Day18)

0 commit comments

Comments
(0)

AltStyle によって変換されたページ (->オリジナル) /