aboutsummaryrefslogtreecommitdiff
path: root/2022/nim/day09
diff options
context:
space:
mode:
authorj-james2022-12-11 23:42:09 +0000
committerj-james2022-12-12 02:09:15 +0000
commit3c8ffda3a5e4ffc583e156d91dd1e55065368248 (patch)
tree14a7ba64aba3d174c38c649d9f70b17cbdd6b63d /2022/nim/day09
parent772305176a24a50ccafe6242c4b612b64e724ef2 (diff)
Day Nine (Nim)
Diffstat (limited to '2022/nim/day09')
-rw-r--r--2022/nim/day09/src/main.nim66
1 files changed, 66 insertions, 0 deletions
diff --git a/2022/nim/day09/src/main.nim b/2022/nim/day09/src/main.nim
new file mode 100644
index 0000000..7432fd2
--- /dev/null
+++ b/2022/nim/day09/src/main.nim
@@ -0,0 +1,66 @@
+# Day 9: Rope Bridge
+import std/[os, strutils, sequtils, sets]
+
+let input = paramStr(1).readFile().strip().split("\n")
+let directions = input.mapIt(it.split(" ")).mapIt((it[0][0], it[1].parseInt()))
+
+type Pos = ref object # must be ref for mutation
+ x: int
+ y: int
+
+type Knot = ref object
+ pos: Pos
+ prev: Knot
+
+func init(_: typedesc[Knot], prev: Knot): Knot =
+ return Knot(pos: Pos(x: 0, y: 0), prev: prev)
+
+proc update(loc, knot: Knot) =
+ let dx = loc.pos.x - knot.pos.x
+ let dy = loc.pos.y - knot.pos.y
+
+ if abs(dx) == 2:
+ knot.pos.x += dx div 2
+ if dy != 0:
+ knot.pos.y += dy div abs(dy)
+ elif abs(dy) == 2:
+ knot.pos.y += dy div 2
+ if dx != 0:
+ knot.pos.x += dx div abs(dx)
+
+proc update(knots: varargs[Knot]) =
+ for i, knot in knots:
+ update(knot.prev, knot)
+
+var visited = initHashSet[(int, int)]()
+var visitedAgain = initHashSet[(int, int)]()
+
+var
+ head = Knot.init(nil)
+ tail = Knot.init(head)
+
+var
+ one = Knot.init(head)
+ two = Knot.init(one)
+ three = Knot.init(two)
+ four = Knot.init(three)
+ five = Knot.init(four)
+ six = Knot.init(five)
+ seven = Knot.init(six)
+ eight = Knot.init(seven)
+ nine = Knot.init(eight)
+
+for dir in directions:
+ for i in 0 ..< dir[1]:
+ if dir[0] == 'R': head.pos.x += 1
+ elif dir[0] == 'L': head.pos.x -= 1
+ elif dir[0] == 'U': head.pos.y += 1
+ elif dir[0] == 'D': head.pos.y -= 1
+
+ update(head, tail)
+ visited.incl((tail.pos.x, tail.pos.y))
+ update(one, two, three, four, five, six, seven, eight, nine)
+ visitedAgain.incl((nine.pos.x, nine.pos.y))
+
+echo visited.len
+echo visitedAgain.len