QOL
This commit is contained in:
13
maze/maze.go
13
maze/maze.go
@@ -9,6 +9,8 @@ import (
|
||||
// A value of 0 is a wall and 1 is a walkable path.
|
||||
type Grid [][]int
|
||||
|
||||
const GOLDEN_RATION_BIT_MIXER = 0x9e3779b97f4a7c15
|
||||
|
||||
var (
|
||||
// ErrInvalidDimensions is returned when width or height are not positive.
|
||||
ErrInvalidDimensions = errors.New("maze dimensions must be greater than zero")
|
||||
@@ -33,7 +35,7 @@ func Generate(width, height int) (Grid, error) {
|
||||
//
|
||||
// The same width, height, and seed always produce the same maze.
|
||||
func GenerateWithSeed(width, height int, seed uint64) (Grid, error) {
|
||||
rng := rand.New(rand.NewPCG(seed, seed^0x9e3779b97f4a7c15))
|
||||
rng := rand.New(rand.NewPCG(seed, seed^GOLDEN_RATION_BIT_MIXER))
|
||||
return generate(width, height, rng.IntN)
|
||||
}
|
||||
|
||||
@@ -60,6 +62,9 @@ func generate(width, height int, intN func(int) int) (Grid, error) {
|
||||
stackY := make([]int, 1, width*height/2)
|
||||
stackX[0], stackY[0] = startX, startY
|
||||
|
||||
// Depth-first backtracking carve:
|
||||
// grow the maze from the current cell into a random unvisited neighbor,
|
||||
// and backtrack when no further expansion is possible.
|
||||
for len(stackX) > 0 {
|
||||
last := len(stackX) - 1
|
||||
x, y := stackX[last], stackY[last]
|
||||
@@ -90,6 +95,7 @@ func generate(width, height int, intN func(int) int) (Grid, error) {
|
||||
}
|
||||
}
|
||||
|
||||
// Choose a top-border entrance that connects to an already carved cell.
|
||||
topChoices := make([]int, 0, width/2)
|
||||
for x := 1; x < width-1; x++ {
|
||||
if grid[1][x] == 1 {
|
||||
@@ -101,6 +107,7 @@ func generate(width, height int, intN func(int) int) (Grid, error) {
|
||||
grid[0][entranceX] = 1
|
||||
}
|
||||
|
||||
// Choose a bottom-border exit that connects to an already carved cell.
|
||||
bottomChoices := make([]int, 0, width/2)
|
||||
for x := 1; x < width-1; x++ {
|
||||
if grid[height-2][x] == 1 {
|
||||
@@ -158,6 +165,8 @@ func Solve(grid Grid) ([][]bool, error) {
|
||||
dx := [4]int{0, 1, 0, -1}
|
||||
dy := [4]int{-1, 0, 1, 0}
|
||||
|
||||
// Breadth-first search from entrance to exit while recording parent links
|
||||
// so the shortest path can be reconstructed afterward.
|
||||
found := false
|
||||
for head := 0; head < len(queue); head++ {
|
||||
idx := queue[head]
|
||||
@@ -192,6 +201,7 @@ func Solve(grid Grid) ([][]bool, error) {
|
||||
return nil, ErrNoPath
|
||||
}
|
||||
|
||||
// Reconstruct the path by following parent pointers backward from exit to entrance.
|
||||
pathCells := make([]bool, width*height)
|
||||
for idx := end; idx != -1; idx = parent[idx] {
|
||||
pathCells[idx] = true
|
||||
@@ -200,6 +210,7 @@ func Solve(grid Grid) ([][]bool, error) {
|
||||
}
|
||||
}
|
||||
|
||||
// Expose the flat path buffer as a 2D matrix aligned with the maze grid.
|
||||
path := make([][]bool, height)
|
||||
for y := 0; y < height; y++ {
|
||||
rowStart := y * width
|
||||
|
||||
Reference in New Issue
Block a user