diff --git a/03dec/main.go b/03dec/main.go new file mode 100644 index 0000000..2b648ce --- /dev/null +++ b/03dec/main.go @@ -0,0 +1,94 @@ +package main + +import ( + "fmt" + "os" + "strconv" +) + +const ( + // directions + W = iota + N + E + S +) + +var ( + // current value + cur int + // current position + x, y int + // current direction + dir int + // grid bounds + xmax, xmin, ymax, ymin int +) + +func main() { + n, err := strconv.Atoi(os.Args[1]) + if err != nil { + os.Exit(1) + } + // move current position in grid and compute change direction, expand grid + for cur < n { + nextMove() + // fmt.Println(cur, x, y) + } + // distance to position + fmt.Println(Abs(x) + Abs(y)) +} + +func nextMove() { + if cur == 0 { + dir = S + } else { + x1, y1 := dirMove() + if outOfBound(x1, y1) { + changeDir() + x1, y1 = dirMove() + } + x, y = x1, y1 + } + cur++ +} + +func dirMove() (int, int) { + switch dir { + case W: + return x - 1, y + case N: + return x, y + 1 + case E: + return x + 1, y + case S: + return x, y - 1 + default: + return x, y + } +} +func outOfBound(x1 int, y1 int) bool { + return x1 > xmax || x1 < xmin || y1 > ymax || y1 < ymin +} +func changeDir() { + switch dir { + case W: + dir = S + ymin-- + case N: + dir = W + xmin-- + case E: + dir = N + ymax++ + case S: + dir = E + xmax++ + } +} +func Abs(n int) int { + if n < 0 { + return -n + } + return n +}