2024-12-10 09:13:42 +00:00
|
|
|
package day_10
|
|
|
|
|
|
|
|
import (
|
|
|
|
"strings"
|
|
|
|
)
|
|
|
|
|
|
|
|
const Empty = '.'
|
|
|
|
|
|
|
|
type Point struct {
|
|
|
|
x, y int
|
|
|
|
height rune
|
|
|
|
}
|
|
|
|
|
|
|
|
type TopographicMap [][]rune
|
|
|
|
|
|
|
|
func (t TopographicMap) InMap(x, y int) bool {
|
|
|
|
return x >= 0 && x < len(t[0]) && y >= 0 && y < len(t)
|
|
|
|
}
|
|
|
|
|
|
|
|
func (t TopographicMap) At(x, y int) rune {
|
|
|
|
if t.InMap(x, y) {
|
|
|
|
return t[y][x]
|
|
|
|
}
|
|
|
|
return Empty
|
|
|
|
}
|
|
|
|
|
|
|
|
// task:https://adventofcode.com/2024/day/10
|
|
|
|
func SolveBasic(input string) int {
|
|
|
|
topographicMap := loadMap(input)
|
|
|
|
solutions := 0
|
|
|
|
for y, line := range topographicMap {
|
|
|
|
for x, pos := range line {
|
|
|
|
if pos == '0' {
|
|
|
|
trails := score(topographicMap, x, y)
|
|
|
|
solutions += trails
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return solutions
|
|
|
|
}
|
|
|
|
|
|
|
|
// task:https://adventofcode.com/2024/day/10#part2
|
|
|
|
func SolveComplex(input string) int {
|
2024-12-10 09:22:05 +00:00
|
|
|
topographicMap := loadMap(input)
|
|
|
|
solutions := 0
|
|
|
|
for y, line := range topographicMap {
|
|
|
|
for x, pos := range line {
|
|
|
|
if pos == '0' {
|
|
|
|
trails := rating(topographicMap, x, y)
|
|
|
|
solutions += trails
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return solutions
|
2024-12-10 09:13:42 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
func score(tMap TopographicMap, x int, y int) int {
|
|
|
|
queue := []Point{{x, y, '0'}}
|
|
|
|
trails := map[Point]bool{}
|
|
|
|
for len(queue) > 0 {
|
|
|
|
p := queue[0]
|
|
|
|
queue = queue[1:]
|
|
|
|
|
|
|
|
if p.height == '9' {
|
|
|
|
trails[p] = true
|
|
|
|
} else {
|
|
|
|
if tMap.At(p.x-1, p.y) == p.height+1 {
|
|
|
|
queue = append(queue, Point{p.x - 1, p.y, p.height + 1})
|
|
|
|
}
|
|
|
|
if tMap.At(p.x, p.y-1) == p.height+1 {
|
|
|
|
queue = append(queue, Point{p.x, p.y - 1, p.height + 1})
|
|
|
|
}
|
|
|
|
if tMap.At(p.x+1, p.y) == p.height+1 {
|
|
|
|
queue = append(queue, Point{p.x + 1, p.y, p.height + 1})
|
|
|
|
}
|
|
|
|
if tMap.At(p.x, p.y+1) == p.height+1 {
|
|
|
|
queue = append(queue, Point{p.x, p.y + 1, p.height + 1})
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return len(trails)
|
|
|
|
}
|
|
|
|
|
2024-12-10 09:22:05 +00:00
|
|
|
func rating(tMap TopographicMap, x int, y int) int {
|
|
|
|
queue := []Point{{x, y, '0'}}
|
|
|
|
trails := 0
|
|
|
|
for len(queue) > 0 {
|
|
|
|
p := queue[0]
|
|
|
|
queue = queue[1:]
|
|
|
|
|
|
|
|
if p.height == '9' {
|
|
|
|
trails++
|
|
|
|
} else {
|
|
|
|
if tMap.At(p.x-1, p.y) == p.height+1 {
|
|
|
|
queue = append(queue, Point{p.x - 1, p.y, p.height + 1})
|
|
|
|
}
|
|
|
|
if tMap.At(p.x, p.y-1) == p.height+1 {
|
|
|
|
queue = append(queue, Point{p.x, p.y - 1, p.height + 1})
|
|
|
|
}
|
|
|
|
if tMap.At(p.x+1, p.y) == p.height+1 {
|
|
|
|
queue = append(queue, Point{p.x + 1, p.y, p.height + 1})
|
|
|
|
}
|
|
|
|
if tMap.At(p.x, p.y+1) == p.height+1 {
|
|
|
|
queue = append(queue, Point{p.x, p.y + 1, p.height + 1})
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return trails
|
|
|
|
}
|
|
|
|
|
2024-12-10 09:13:42 +00:00
|
|
|
func loadMap(input string) TopographicMap {
|
|
|
|
input = strings.ReplaceAll(input, "\r", "")
|
|
|
|
topographicMap := TopographicMap{}
|
|
|
|
for _, line := range strings.Split(input, "\n") {
|
|
|
|
topographicMap = append(topographicMap, []rune(line))
|
|
|
|
}
|
|
|
|
return topographicMap
|
|
|
|
}
|