2022 Day 9 Complete!
This commit is contained in:
parent
30b00e68a4
commit
f5270a396a
2000
2022/day09/input
Normal file
2000
2022/day09/input
Normal file
File diff suppressed because it is too large
Load Diff
166
2022/day09/main.go
Normal file
166
2022/day09/main.go
Normal file
@ -0,0 +1,166 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
h "git.bullercodeworks.com/brian/adventofcode/helpers"
|
||||
)
|
||||
|
||||
var sleepTime = (time.Second / 5)
|
||||
|
||||
var minx, miny, maxx, maxy int
|
||||
|
||||
func main() {
|
||||
inp := h.StdinToStringSlice()
|
||||
|
||||
watch := len(os.Args) > 1 && strings.HasPrefix(os.Args[1], "-w")
|
||||
if watch {
|
||||
if strings.Contains(os.Args[1], "=") {
|
||||
pts := strings.Split(os.Args[1], "=")
|
||||
sleepTime = (time.Second / time.Duration(h.Atoi(pts[1])))
|
||||
}
|
||||
}
|
||||
simulate(inp, 10, watch)
|
||||
}
|
||||
|
||||
func buildInstructions(inp []string) []byte {
|
||||
var inst []byte
|
||||
for i := range inp {
|
||||
dir, count := inp[i][0], h.Atoi(inp[i][2:])
|
||||
for j := 0; j < count; j++ {
|
||||
inst = append(inst, dir)
|
||||
}
|
||||
}
|
||||
return inst
|
||||
}
|
||||
|
||||
func simulate(inp []string, knotCount int, watch bool) {
|
||||
if watch {
|
||||
fmt.Print(h.CLEAR_SCREEN)
|
||||
}
|
||||
visited := make(map[h.Coordinate]bool)
|
||||
inst := buildInstructions(inp)
|
||||
var knots []h.Coordinate
|
||||
for i := 0; i < knotCount; i++ {
|
||||
knots = append(knots, h.Coordinate{X: 0, Y: 0})
|
||||
}
|
||||
if watch {
|
||||
fmt.Println("# Part 1")
|
||||
printVisits(visited, knots)
|
||||
}
|
||||
for i, dir := range inst {
|
||||
moveHead(dir, knots)
|
||||
visited[knots[len(knots)-1]] = true
|
||||
if watch {
|
||||
time.Sleep(sleepTime)
|
||||
fmt.Print(h.CLEAR_SCREEN)
|
||||
fmt.Printf("# Part 1 (%d/%d)\n", i, len(inst))
|
||||
printVisits(visited, knots)
|
||||
}
|
||||
}
|
||||
if watch {
|
||||
time.Sleep(sleepTime)
|
||||
fmt.Print(h.CLEAR_SCREEN)
|
||||
}
|
||||
fmt.Println("# Part 1")
|
||||
if watch {
|
||||
printVisits(visited, knots)
|
||||
}
|
||||
fmt.Printf("Tail visited %d positions\n", len(visited))
|
||||
}
|
||||
|
||||
func moveHead(dir byte, knots []h.Coordinate) {
|
||||
prevKnots := make([]h.Coordinate, len(knots))
|
||||
copy(prevKnots, knots)
|
||||
switch dir {
|
||||
case 'U':
|
||||
knots[0] = knots[0].North()
|
||||
case 'R':
|
||||
knots[0] = knots[0].East()
|
||||
case 'D':
|
||||
knots[0] = knots[0].South()
|
||||
case 'L':
|
||||
knots[0] = knots[0].West()
|
||||
}
|
||||
if knots[0].X < minx {
|
||||
minx = knots[0].X
|
||||
}
|
||||
if knots[0].X > maxx {
|
||||
maxx = knots[0].X
|
||||
}
|
||||
if knots[0].Y < miny {
|
||||
miny = knots[0].Y
|
||||
}
|
||||
if knots[0].Y > maxy {
|
||||
maxy = knots[0].Y
|
||||
}
|
||||
for i := 1; i < len(knots); i++ {
|
||||
// Go through all knots and check if any need to move
|
||||
if !knots[i].Equals(knots[i-1]) && !knots[i].Adjacent(knots[i-1]) {
|
||||
if knots[i].X == knots[i-1].X {
|
||||
// Same column
|
||||
if knots[i].Y < knots[i-1].Y {
|
||||
knots[i].Y++
|
||||
} else {
|
||||
knots[i].Y--
|
||||
}
|
||||
} else if knots[i].Y == knots[i-1].Y {
|
||||
// Save row
|
||||
if knots[i].X < knots[i-1].X {
|
||||
knots[i].X++
|
||||
} else {
|
||||
knots[i].X--
|
||||
}
|
||||
} else {
|
||||
// Not in the same row or column
|
||||
if knots[i].X < knots[i-1].X {
|
||||
knots[i].X++
|
||||
} else {
|
||||
knots[i].X--
|
||||
}
|
||||
if knots[i].Y < knots[i-1].Y {
|
||||
knots[i].Y++
|
||||
} else {
|
||||
knots[i].Y--
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// If one knot didn't need to move, none behind it will
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func printVisits(m map[h.Coordinate]bool, knots []h.Coordinate) {
|
||||
for y := miny; y <= maxy; y++ {
|
||||
for x := minx; x <= maxx; x++ {
|
||||
var isKnot bool
|
||||
for i := range knots {
|
||||
if knots[i].X == x && knots[i].Y == y {
|
||||
isKnot = true
|
||||
var bt byte
|
||||
if i == 0 {
|
||||
bt = 'H'
|
||||
} else {
|
||||
bt = '0' + byte(i)
|
||||
}
|
||||
fmt.Print(string(bt))
|
||||
break
|
||||
}
|
||||
}
|
||||
if !isKnot {
|
||||
if v, ok := m[h.Coordinate{X: x, Y: y}]; ok && v {
|
||||
fmt.Print("#")
|
||||
} else {
|
||||
fmt.Print(".")
|
||||
}
|
||||
}
|
||||
}
|
||||
fmt.Println()
|
||||
}
|
||||
fmt.Printf("Bridge: %s\n", knots)
|
||||
fmt.Println()
|
||||
}
|
311
2022/day09/problem
Normal file
311
2022/day09/problem
Normal file
@ -0,0 +1,311 @@
|
||||
Advent of Code
|
||||
|
||||
• [About]
|
||||
• [Events]
|
||||
• [Shop]
|
||||
• [Settings]
|
||||
• [Log Out]
|
||||
|
||||
br0xen (AoC++) 16*
|
||||
|
||||
0.0.0.0:2022
|
||||
|
||||
• [Calendar]
|
||||
• [AoC++]
|
||||
• [Sponsors]
|
||||
• [Leaderboard]
|
||||
• [Stats]
|
||||
|
||||
Our sponsors help make Advent of Code possible:
|
||||
King - At King, we create unforgettable games (like Candy Crush) that are loved around the world. Join us to bring
|
||||
moments of magic to hundreds of millions of people every single day!
|
||||
|
||||
--- Day 9: Rope Bridge ---
|
||||
|
||||
This rope bridge creaks as you walk along it. You aren't sure how old it is, or whether it can even support your weight.
|
||||
|
||||
It seems to support the Elves just fine, though. The bridge spans a gorge which was carved out by the massive river far
|
||||
below you.
|
||||
|
||||
You step carefully; as you do, the ropes stretch and twist. You decide to distract yourself by modeling rope physics;
|
||||
maybe you can even figure out where not to step.
|
||||
|
||||
Consider a rope with a knot at each end; these knots mark the head and the tail of the rope. If the head moves far
|
||||
enough away from the tail, the tail is pulled toward the head.
|
||||
|
||||
Due to nebulous reasoning involving Planck lengths, you should be able to model the positions of the knots on a
|
||||
two-dimensional grid. Then, by following a hypothetical series of motions (your puzzle input) for the head, you can
|
||||
determine how the tail will move.
|
||||
|
||||
Due to the aforementioned Planck lengths, the rope must be quite short; in fact, the head (H) and tail (T) must always
|
||||
be touching (diagonally adjacent and even overlapping both count as touching):
|
||||
|
||||
....
|
||||
.TH.
|
||||
....
|
||||
|
||||
....
|
||||
.H..
|
||||
..T.
|
||||
....
|
||||
|
||||
...
|
||||
.H. (H covers T)
|
||||
...
|
||||
|
||||
If the head is ever two steps directly up, down, left, or right from the tail, the tail must also move one step in that
|
||||
direction so it remains close enough:
|
||||
|
||||
..... ..... .....
|
||||
.TH.. -> .T.H. -> ..TH.
|
||||
..... ..... .....
|
||||
|
||||
... ... ...
|
||||
.T. .T. ...
|
||||
.H. -> ... -> .T.
|
||||
... .H. .H.
|
||||
... ... ...
|
||||
|
||||
Otherwise, if the head and tail aren't touching and aren't in the same row or column, the tail always moves one step
|
||||
diagonally to keep up:
|
||||
|
||||
..... ..... .....
|
||||
..... ..H.. ..H..
|
||||
..H.. -> ..... -> ..T..
|
||||
.T... .T... .....
|
||||
..... ..... .....
|
||||
|
||||
..... ..... .....
|
||||
..... ..... .....
|
||||
..H.. -> ...H. -> ..TH.
|
||||
.T... .T... .....
|
||||
..... ..... .....
|
||||
|
||||
You just need to work out where the tail goes as the head follows a series of motions. Assume the head and the tail both
|
||||
start at the same position, overlapping.
|
||||
|
||||
For example:
|
||||
|
||||
R 4
|
||||
U 4
|
||||
L 3
|
||||
D 1
|
||||
R 4
|
||||
D 1
|
||||
L 5
|
||||
R 2
|
||||
|
||||
This series of motions moves the head right four steps, then up four steps, then left three steps, then down one step,
|
||||
and so on. After each step, you'll need to update the position of the tail if the step means the head is no longer
|
||||
adjacent to the tail. Visually, these motions occur as follows (s marks the starting position as a reference point):
|
||||
|
||||
== Initial State ==
|
||||
|
||||
......
|
||||
......
|
||||
......
|
||||
......
|
||||
H..... (H covers T, s)
|
||||
|
||||
== R 4 ==
|
||||
|
||||
......
|
||||
......
|
||||
......
|
||||
......
|
||||
TH.... (T covers s)
|
||||
|
||||
......
|
||||
......
|
||||
......
|
||||
......
|
||||
sTH...
|
||||
|
||||
......
|
||||
......
|
||||
......
|
||||
......
|
||||
s.TH..
|
||||
|
||||
......
|
||||
......
|
||||
......
|
||||
......
|
||||
s..TH.
|
||||
|
||||
== U 4 ==
|
||||
|
||||
......
|
||||
......
|
||||
......
|
||||
....H.
|
||||
s..T..
|
||||
|
||||
......
|
||||
......
|
||||
....H.
|
||||
....T.
|
||||
s.....
|
||||
|
||||
......
|
||||
....H.
|
||||
....T.
|
||||
......
|
||||
s.....
|
||||
|
||||
....H.
|
||||
....T.
|
||||
......
|
||||
......
|
||||
s.....
|
||||
|
||||
== L 3 ==
|
||||
|
||||
...H..
|
||||
....T.
|
||||
......
|
||||
......
|
||||
s.....
|
||||
|
||||
..HT..
|
||||
......
|
||||
......
|
||||
......
|
||||
s.....
|
||||
|
||||
.HT...
|
||||
......
|
||||
......
|
||||
......
|
||||
s.....
|
||||
|
||||
== D 1 ==
|
||||
|
||||
..T...
|
||||
.H....
|
||||
......
|
||||
......
|
||||
s.....
|
||||
|
||||
== R 4 ==
|
||||
|
||||
..T...
|
||||
..H...
|
||||
......
|
||||
......
|
||||
s.....
|
||||
|
||||
..T...
|
||||
...H..
|
||||
......
|
||||
......
|
||||
s.....
|
||||
|
||||
......
|
||||
...TH.
|
||||
......
|
||||
......
|
||||
s.....
|
||||
|
||||
......
|
||||
....TH
|
||||
......
|
||||
......
|
||||
s.....
|
||||
|
||||
== D 1 ==
|
||||
|
||||
......
|
||||
....T.
|
||||
.....H
|
||||
......
|
||||
s.....
|
||||
|
||||
== L 5 ==
|
||||
|
||||
......
|
||||
....T.
|
||||
....H.
|
||||
......
|
||||
s.....
|
||||
|
||||
......
|
||||
....T.
|
||||
...H..
|
||||
......
|
||||
s.....
|
||||
|
||||
......
|
||||
......
|
||||
..HT..
|
||||
......
|
||||
s.....
|
||||
|
||||
......
|
||||
......
|
||||
.HT...
|
||||
......
|
||||
s.....
|
||||
|
||||
......
|
||||
......
|
||||
HT....
|
||||
......
|
||||
s.....
|
||||
|
||||
== R 2 ==
|
||||
|
||||
......
|
||||
......
|
||||
.H.... (H covers T)
|
||||
......
|
||||
s.....
|
||||
|
||||
......
|
||||
......
|
||||
.TH...
|
||||
......
|
||||
s.....
|
||||
|
||||
After simulating the rope, you can count up all of the positions the tail visited at least once. In this diagram, s
|
||||
again marks the starting position (which the tail also visited) and # marks other positions the tail visited:
|
||||
|
||||
..##..
|
||||
...##.
|
||||
.####.
|
||||
....#.
|
||||
s###..
|
||||
|
||||
So, there are 13 positions the tail visited at least once.
|
||||
|
||||
Simulate your complete hypothetical series of motions. How many positions does the tail of the rope visit at least once?
|
||||
|
||||
To begin, get your puzzle input.
|
||||
|
||||
Answer: _____________________ [ [Submit] ]
|
||||
|
||||
You can also [Shareon Twitter Mastodon] this puzzle.
|
||||
|
||||
References
|
||||
|
||||
Visible links
|
||||
. https://adventofcode.com/
|
||||
. https://adventofcode.com/2022/about
|
||||
. https://adventofcode.com/2022/events
|
||||
. https://teespring.com/stores/advent-of-code
|
||||
. https://adventofcode.com/2022/settings
|
||||
. https://adventofcode.com/2022/auth/logout
|
||||
. Advent of Code Supporter
|
||||
https://adventofcode.com/2022/support
|
||||
. https://adventofcode.com/2022
|
||||
. https://adventofcode.com/2022
|
||||
. https://adventofcode.com/2022/support
|
||||
. https://adventofcode.com/2022/sponsors
|
||||
. https://adventofcode.com/2022/leaderboard
|
||||
. https://adventofcode.com/2022/stats
|
||||
. https://adventofcode.com/2022/sponsors
|
||||
. https://careers.king.com/
|
||||
. https://en.wikipedia.org/wiki/Planck_units#Planck_length
|
||||
. https://adventofcode.com/2022/day/9/input
|
||||
. https://twitter.com/intent/tweet?text=%22Rope+Bridge%22+%2D+Day+9+%2D+Advent+of+Code+2022&url=https%3A%2F%2Fadventofcode%2Ecom%2F2022%2Fday%2F9&related=ericwastl&hashtags=AdventOfCode
|
||||
. javascript:void(0);
|
8
2022/day09/testinput
Normal file
8
2022/day09/testinput
Normal file
@ -0,0 +1,8 @@
|
||||
R 4
|
||||
U 4
|
||||
L 3
|
||||
D 1
|
||||
R 4
|
||||
D 1
|
||||
L 5
|
||||
R 2
|
8
2022/day09/testinput2
Normal file
8
2022/day09/testinput2
Normal file
@ -0,0 +1,8 @@
|
||||
R 5
|
||||
U 8
|
||||
L 8
|
||||
D 3
|
||||
R 17
|
||||
D 10
|
||||
L 25
|
||||
U 20
|
@ -97,3 +97,13 @@ func (c Coordinate) Distance(t Coordinate) int {
|
||||
func (c Coordinate) Equals(c2 Coordinate) bool {
|
||||
return c.X == c2.X && c.Y == c2.Y
|
||||
}
|
||||
func (c Coordinate) Adjacent(c2 Coordinate) bool {
|
||||
return c2.Equals(c.North()) ||
|
||||
c2.Equals(c.NE()) ||
|
||||
c2.Equals(c.East()) ||
|
||||
c2.Equals(c.SE()) ||
|
||||
c2.Equals(c.South()) ||
|
||||
c2.Equals(c.SW()) ||
|
||||
c2.Equals(c.West()) ||
|
||||
c2.Equals(c.NW())
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user