adventofcode/2019/day15/maze.go

147 lines
2.6 KiB
Go

package main
import (
"fmt"
helpers "git.bullercodeworks.com/brian/adventofcode/helpers"
)
const (
MAZE_UNKNOWN = -1
MAZE_WALL = 0
MAZE_EMPTY = 1
MAZE_O2SYS = 2
)
const (
DIR_N = 1
DIR_S = 2
DIR_W = 3
DIR_E = 4
)
type Maze struct {
maze map[string]int
maxX, minX int
maxY, minY int
bot *helpers.Coordinate
path []*helpers.Coordinate
dirHistory []int
dnt bool
startCoord *helpers.Coordinate
o2Coord *helpers.Coordinate
}
func NewMaze() *Maze {
m := &Maze{
maze: make(map[string]int),
maxX: helpers.MIN_INT,
minX: helpers.MAX_INT,
maxY: helpers.MIN_INT,
minY: helpers.MAX_INT,
bot: helpers.NewCoordinate(0, 0),
startCoord: helpers.NewCoordinate(0, 0),
}
m.path = append(m.path, helpers.NewCoordinate(0, 0))
return m
}
func (m *Maze) SetCoord(c *helpers.Coordinate, val int) {
if val == 2 {
m.o2Coord = c
}
m.maze[c.String()] = val
if m.maxX < c.X {
m.maxX = c.X
}
if m.minX > c.X {
m.minX = c.X
}
if m.maxY < c.Y {
m.maxY = c.Y
}
if m.minY > c.Y {
m.minY = c.Y
}
}
func (m *Maze) GetCoord(c *helpers.Coordinate) int {
v, ok := m.maze[c.String()]
if !ok {
return MAZE_UNKNOWN
}
return v
}
func (m *Maze) GetDirFromBot(dir int) *helpers.Coordinate {
switch dir {
case DIR_N:
return m.bot.GetNorthCoord()
case DIR_E:
return m.bot.GetEastCoord()
case DIR_S:
return m.bot.GetSouthCoord()
case DIR_W:
return m.bot.GetWestCoord()
}
return nil
}
func (m *Maze) MoveBot(dir int) bool {
dest := m.GetDirFromBot(dir)
if m.GetCoord(dest) == MAZE_UNKNOWN || m.GetCoord(dest) == MAZE_WALL {
return false
}
m.bot.X, m.bot.Y = dest.X, dest.Y
if !m.dnt {
m.path = append(m.path, helpers.NewCoordinate(m.bot.X, m.bot.Y))
m.dirHistory = append(m.dirHistory, dir)
}
m.dnt = false
return true
}
func (m *Maze) GetDirectionToLast() int {
if len(m.dirHistory) == 0 {
return -1
}
m.dnt = true
var dir int
dir, m.dirHistory = m.dirHistory[len(m.dirHistory)-1], m.dirHistory[:len(m.dirHistory)-1]
switch dir {
case DIR_N:
return DIR_S
case DIR_S:
return DIR_N
case DIR_W:
return DIR_E
case DIR_E:
return DIR_W
}
return -1
}
func (m *Maze) Print() {
for y := m.minY; y <= m.maxY; y++ {
for x := m.minX; x <= m.maxX; x++ {
c := helpers.NewCoordinate(x, y)
if m.bot.Equals(*c) {
fmt.Print("%")
} else {
switch m.GetCoord(c) {
case MAZE_UNKNOWN:
fmt.Print("~")
case MAZE_WALL:
fmt.Print("#")
case MAZE_EMPTY:
fmt.Print(" ")
case MAZE_O2SYS:
fmt.Print("O")
}
}
}
fmt.Println()
}
}