Skip to content

Commit b17a5e6

Browse files
committed
Add day 09
This was a hekkin hekker ...
1 parent 0f12f09 commit b17a5e6

File tree

6 files changed

+2187
-0
lines changed

6 files changed

+2187
-0
lines changed

09/example-2.txt

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
R 5
2+
U 8
3+
L 8
4+
D 3
5+
R 17
6+
D 10
7+
L 25
8+
U 20

09/example.txt

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
R 4
2+
U 4
3+
L 3
4+
D 1
5+
R 4
6+
D 1
7+
L 5
8+
R 2

09/main.go

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
package main
2+
3+
import (
4+
"fmt"
5+
"strconv"
6+
"strings"
7+
8+
"github.com/vimkat/aoc-2022/util"
9+
)
10+
11+
func main() {
12+
part1("example.txt")
13+
part1("puzzle.txt")
14+
fmt.Println()
15+
part2("example.txt")
16+
part2("example-2.txt")
17+
part2("puzzle.txt")
18+
}
19+
20+
func part1(path string) { simulateRope(path, 2) }
21+
func part2(path string) { simulateRope(path, 10) }
22+
23+
func simulateRope(path string, ropeLength int) {
24+
rope := NewRope(ropeLength)
25+
26+
for line := range util.ReadByLines(path) {
27+
parsed := strings.Split(line, " ")
28+
repeat := util.MustValue(strconv.Atoi(parsed[1]))
29+
30+
for i := 0; i < repeat; i++ {
31+
switch parsed[0] {
32+
case "L":
33+
rope.Move(-1, 0)
34+
case "R":
35+
rope.Move(1, 0)
36+
case "U":
37+
rope.Move(0, -1)
38+
case "D":
39+
rope.Move(0, 1)
40+
}
41+
}
42+
43+
// Print steps
44+
// if strings.HasPrefix(path, "example") {
45+
// rope.PrettyPrint(35, 35, 15, 15)
46+
// fmt.Println()
47+
// }
48+
}
49+
50+
fmt.Println(len(rope.Visited()))
51+
}

09/model.go

Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,103 @@
1+
package main
2+
3+
import (
4+
"fmt"
5+
6+
"github.com/vimkat/aoc-2022/util"
7+
)
8+
9+
type Pos struct{ x, y int }
10+
11+
func (p Pos) String() string { return fmt.Sprintf("(%d/%d)", p.x, p.y) }
12+
func (p Pos) Add(x, y int) Pos { return Pos{p.x + x, p.y + y} }
13+
14+
func (p Pos) IsAdjacent(other Pos) bool {
15+
return util.Abs(p.x-other.x) <= 1 && util.Abs(p.y-other.y) <= 1
16+
}
17+
18+
func (p Pos) MakeAdjacentTo(other Pos) Pos {
19+
if p.IsAdjacent(other) {
20+
return p
21+
}
22+
23+
if p.x == other.x {
24+
return Pos{other.x, other.y - util.Sign(other.y-p.y)}
25+
}
26+
27+
if p.y == other.y {
28+
return Pos{other.x - util.Sign(other.x-p.x), other.y}
29+
}
30+
31+
dx := util.Abs(other.x - p.x)
32+
dy := util.Abs(other.y - p.y)
33+
34+
if dx < dy {
35+
return Pos{other.x, other.y - util.Sign(other.y-p.y)}
36+
}
37+
38+
if dy < dx {
39+
return Pos{other.x - util.Sign(other.x-p.x), other.y}
40+
}
41+
42+
return Pos{
43+
other.x - util.Sign(other.x-p.x),
44+
other.y - util.Sign(other.y-p.y),
45+
}
46+
}
47+
48+
type Rope struct {
49+
rope []Pos
50+
visited map[Pos]int
51+
}
52+
53+
func NewRope(ropeLength int) *Rope {
54+
r := Rope{
55+
rope: make([]Pos, ropeLength),
56+
visited: make(map[Pos]int),
57+
}
58+
59+
// Start position has already been visited
60+
r.visited[Pos{0, 0}] = 1
61+
62+
return &r
63+
}
64+
65+
func (r *Rope) Move(dx, dy int) {
66+
// Move the head
67+
r.rope[0] = r.rope[0].Add(dx, dy)
68+
69+
// Update the tail(s)
70+
for i := 1; i < len(r.rope); i++ {
71+
r.rope[i] = r.rope[i].MakeAdjacentTo(r.rope[i-1])
72+
}
73+
74+
// Mark visited
75+
val := r.visited[r.rope[len(r.rope)-1]]
76+
val += 1
77+
r.visited[r.rope[len(r.rope)-1]] = val
78+
}
79+
80+
func (r Rope) Visited() map[Pos]int {
81+
return r.visited
82+
}
83+
84+
func (r Rope) PrettyPrint(width, height, centerX, centerY int) {
85+
grid := make([][]rune, height)
86+
for row := 0; row < height; row++ {
87+
grid[row] = make([]rune, width)
88+
for col := 0; col < width; col++ {
89+
grid[row][col] = '.'
90+
}
91+
}
92+
93+
grid[centerY][centerX] = 'S'
94+
95+
// Print knots
96+
for i, knot := range r.rope {
97+
grid[knot.y+centerY][knot.x+centerX] = rune(i + '0')
98+
}
99+
100+
for row := 0; row < height; row++ {
101+
fmt.Println(string(grid[row]))
102+
}
103+
}

0 commit comments

Comments
 (0)