Files
advent-of-code-2025/internal/grid/grid.go
T

129 lines
2.8 KiB
Go
Raw Normal View History

2025-12-07 07:59:27 -06:00
package grid
import (
2025-12-08 05:39:47 -06:00
"strings"
"github.com/StevanFreeborn/advent-of-code-2025/internal/move"
"github.com/StevanFreeborn/advent-of-code-2025/internal/position"
)
2025-12-07 07:59:27 -06:00
type Grid interface {
NumberOfRows() int
NumberOfColumns() int
InBounds(position.Position) bool
GetValueAt(position.Position) string
GetSameNeighborsOf(position.Position, []move.Move) []position.Position
Positions() map[position.Position]string
2025-12-08 05:39:47 -06:00
SetValuesAt(positions []position.Position, value string)
2025-12-07 07:59:27 -06:00
}
type grid struct {
numberOfRows int
numberOfColumns int
positions map[position.Position]string
2025-12-07 07:59:27 -06:00
}
2025-12-08 05:39:47 -06:00
func New(positions map[position.Position]string) Grid {
return grid{positions: positions}
}
func From(input []string) Grid {
2025-12-07 07:59:27 -06:00
numberOfRows := len(input)
numberOfColumns := len(input[0])
positions := map[position.Position]string{}
2025-12-07 07:59:27 -06:00
for row := range numberOfRows {
for column := range numberOfColumns {
value := string(input[row][column])
pos := position.From(row, column)
2025-12-07 07:59:27 -06:00
positions[pos] = value
}
}
return grid{
numberOfRows: numberOfRows,
numberOfColumns: numberOfColumns,
positions: positions,
2025-12-07 07:59:27 -06:00
}
}
func (g grid) NumberOfRows() int {
return g.numberOfRows
}
2025-12-07 07:59:27 -06:00
func (g grid) NumberOfColumns() int {
return g.numberOfColumns
}
func (g grid) InBounds(pos position.Position) bool {
_, ok := g.positions[pos]
return ok
2025-12-07 07:59:27 -06:00
}
func (g grid) GetValueAt(pos position.Position) string {
return g.positions[pos]
2025-12-07 07:59:27 -06:00
}
func (g grid) GetSameNeighborsOf(pos position.Position, moves []move.Move) []position.Position {
similarNeighbors := []position.Position{}
originalValue := g.GetValueAt(pos)
2025-12-07 07:59:27 -06:00
for _, m := range moves {
postionRow := pos.Row()
positionColumn := pos.Column()
2025-12-07 07:59:27 -06:00
neighborRow := postionRow + m.NumberOfRows()
neighborColumn := positionColumn + m.NumberOfColumns()
neighborPos := position.From(neighborRow, neighborColumn)
2025-12-07 07:59:27 -06:00
if g.InBounds(neighborPos) == false {
continue
}
2025-12-07 07:59:27 -06:00
neighborValue := g.GetValueAt(neighborPos)
2025-12-07 07:59:27 -06:00
if neighborValue != originalValue {
continue
}
2025-12-07 07:59:27 -06:00
similarNeighbors = append(similarNeighbors, neighborPos)
}
return similarNeighbors
2025-12-07 07:59:27 -06:00
}
func (g grid) Positions() map[position.Position]string {
positions := map[position.Position]string{}
for pos, value := range g.positions {
newPosition := position.From(pos.Row(), pos.Column())
positions[newPosition] = value
}
return positions
}
2025-12-08 05:39:47 -06:00
func (g grid) SetValuesAt(positions []position.Position, value string) {
for _, pos := range positions {
g.positions[pos] = value
}
}
func (g grid) String() string {
var rowString strings.Builder
for row := range g.numberOfRows {
var colString strings.Builder
for col := range g.numberOfColumns {
pos := position.From(row, col)
value := g.positions[pos]
colString.WriteString(value)
}
rowString.WriteString(colString.String() + "\n")
}
return rowString.String()
}