aboutsummaryrefslogtreecommitdiff
path: root/aoc2017-gleam/src/aoc_2017/day_13.gleam
diff options
context:
space:
mode:
Diffstat (limited to 'aoc2017-gleam/src/aoc_2017/day_13.gleam')
-rw-r--r--aoc2017-gleam/src/aoc_2017/day_13.gleam75
1 files changed, 75 insertions, 0 deletions
diff --git a/aoc2017-gleam/src/aoc_2017/day_13.gleam b/aoc2017-gleam/src/aoc_2017/day_13.gleam
new file mode 100644
index 0000000..7d3df0b
--- /dev/null
+++ b/aoc2017-gleam/src/aoc_2017/day_13.gleam
@@ -0,0 +1,75 @@
+import gleam/int
+import gleam/list
+import gleam/string
+
+pub type Direction {
+ North
+ Northeast
+ Northwest
+ South
+ Southeast
+ Southwest
+}
+
+type HexPosition {
+ HexPosition(x: Int, y: Int, z: Int)
+}
+
+const start = HexPosition(0, 0, 0)
+
+fn to_direction(str: String) -> Direction {
+ case str {
+ "n" -> North
+ "ne" -> Northeast
+ "nw" -> Northwest
+ "s" -> South
+ "se" -> Southeast
+ "sw" -> Southwest
+ _ -> panic as "unrecognized direction"
+ }
+}
+
+fn distance(hp1: HexPosition, hp2: HexPosition) -> Int {
+ {
+ int.absolute_value(hp1.x - hp2.x)
+ + int.absolute_value(hp1.y - hp2.y)
+ + int.absolute_value(hp1.z - hp2.z)
+ }
+ / 2
+}
+
+fn move(p, direction) -> HexPosition {
+ case direction {
+ North -> HexPosition(..p, y: p.y + 1, z: p.z - 1)
+ South -> HexPosition(..p, y: p.y - 1, z: p.z + 1)
+ Northeast -> HexPosition(..p, x: p.x + 1, z: p.z - 1)
+ Southwest -> HexPosition(..p, x: p.x - 1, z: p.z + 1)
+ Southeast -> HexPosition(..p, x: p.x + 1, y: p.y - 1)
+ Northwest -> HexPosition(..p, x: p.x - 1, y: p.y + 1)
+ }
+}
+
+pub fn parse(input: String) -> List(Direction) {
+ input
+ |> string.split(",")
+ |> list.map(to_direction)
+}
+
+pub fn pt_1(input: List(Direction)) {
+ do_walk(input, start, 0).0
+}
+
+pub fn pt_2(input: List(Direction)) {
+ do_walk(input, start, 0).1
+}
+
+fn do_walk(steps, position, max) {
+ case steps {
+ [] -> #(distance(position, HexPosition(0, 0, 0)), max)
+ [next, ..rest] -> {
+ let new_position = move(position, next)
+ let new_max = int.max(max, distance(new_position, start))
+ do_walk(rest, new_position, new_max)
+ }
+ }
+}