2024 day 18 Complete
This commit is contained in:
3450
2024/day18/input
Normal file
3450
2024/day18/input
Normal file
File diff suppressed because it is too large
Load Diff
113
2024/day18/main.go
Normal file
113
2024/day18/main.go
Normal file
@@ -0,0 +1,113 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
h "git.bullercodeworks.com/brian/adventofcode/helpers"
|
||||
)
|
||||
|
||||
func main() {
|
||||
inp := h.StdinToStringSlice()
|
||||
// size, bytes := 6, 12 // Test Input
|
||||
size, bytes := 70, 1024 // Actual Input
|
||||
part1(inp, size, bytes)
|
||||
fmt.Println()
|
||||
part2(inp, size, bytes)
|
||||
}
|
||||
|
||||
func part1(inp []string, size, bytes int) {
|
||||
// bytes:= 12 // Test Input
|
||||
m := h.NewCoordByteMap()
|
||||
m.BRX, m.BRY = size, size
|
||||
drops := parseInput(inp)
|
||||
for i := 0; i < bytes; i++ {
|
||||
m.Put(drops[i], '#')
|
||||
}
|
||||
|
||||
fmt.Println("# Part 1")
|
||||
fmt.Println(FindShortestPath(m, func(a, b State) bool {
|
||||
return a.cnt+a.dist < b.cnt+b.dist
|
||||
}))
|
||||
}
|
||||
|
||||
func part2(inp []string, size, bytes int) {
|
||||
m := h.NewCoordByteMap()
|
||||
m.BRX, m.BRY = size, size
|
||||
drops := parseInput(inp)
|
||||
// We can skip up to 'bytes', part1 showed that that many work
|
||||
for i := 0; i < bytes; i++ {
|
||||
m.Put(drops[i], '#')
|
||||
}
|
||||
|
||||
fmt.Println("# Part 2")
|
||||
for tm, b := range drops[bytes+1:] {
|
||||
m.Put(b, '#')
|
||||
if FindShortestPath(m, func(a, b State) bool {
|
||||
return a.dist < b.dist
|
||||
}) == -1 {
|
||||
fmt.Printf("Blocked at %d: %s\n", bytes+tm, b.String())
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func parseInput(inp []string) []h.Coordinate {
|
||||
var ret []h.Coordinate
|
||||
for i := range inp {
|
||||
c := h.Coordinate{}
|
||||
fmt.Sscanf(inp[i], "%d,%d", &c.X, &c.Y)
|
||||
ret = append(ret, c)
|
||||
}
|
||||
return ret
|
||||
}
|
||||
|
||||
type State struct {
|
||||
c h.Coordinate
|
||||
cnt int
|
||||
dist int
|
||||
}
|
||||
|
||||
func FindShortestPath(inp h.CoordByteMap, less func(a, b State) bool) int {
|
||||
visited := make(map[h.Coordinate]State)
|
||||
end := h.Coordinate{X: inp.BRX, Y: inp.BRY}
|
||||
start := h.Coordinate{X: 0, Y: 0}
|
||||
startState := State{
|
||||
c: start,
|
||||
cnt: 0,
|
||||
dist: start.Distance(end),
|
||||
}
|
||||
queue := h.NewHeap[State](less)
|
||||
queue.Push(startState)
|
||||
|
||||
for queue.Len() > 0 {
|
||||
step := queue.Pop()
|
||||
if step.c.Equals(end) {
|
||||
visited[end] = step
|
||||
break
|
||||
}
|
||||
|
||||
if _, ok := visited[step.c]; ok {
|
||||
continue
|
||||
}
|
||||
visited[step.c] = step
|
||||
// Find next steps
|
||||
for _, n := range step.c.GetOrthNeighbors() {
|
||||
if !inp.ContainsCoord(n) || inp.Get(n) == '#' {
|
||||
continue
|
||||
}
|
||||
if _, ok := visited[n]; ok {
|
||||
continue
|
||||
}
|
||||
nState := State{
|
||||
c: n,
|
||||
cnt: step.cnt + 1,
|
||||
dist: n.Distance(end),
|
||||
}
|
||||
queue.Push(nState)
|
||||
}
|
||||
}
|
||||
if v, ok := visited[end]; ok {
|
||||
return v.cnt
|
||||
}
|
||||
return -1
|
||||
}
|
25
2024/day18/testinput
Normal file
25
2024/day18/testinput
Normal file
@@ -0,0 +1,25 @@
|
||||
5,4
|
||||
4,2
|
||||
4,5
|
||||
3,0
|
||||
2,1
|
||||
6,3
|
||||
2,4
|
||||
1,5
|
||||
0,6
|
||||
3,3
|
||||
2,6
|
||||
5,1
|
||||
1,2
|
||||
5,5
|
||||
2,5
|
||||
6,5
|
||||
1,4
|
||||
0,4
|
||||
6,4
|
||||
1,1
|
||||
6,1
|
||||
1,0
|
||||
0,5
|
||||
1,6
|
||||
2,0
|
Reference in New Issue
Block a user