model

package
v0.7.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Apr 9, 2023 License: MIT Imports: 9 Imported by: 0

Documentation

Index

Constants

View Source
const (
	WHITE = " "
	BLACK = "*"
)

The initial values of a cell

View Source
const ALPHABET = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"

Variables

This section is empty.

Functions

func Complement

func Complement(ilist []int) []int

Complement is a function that will return a list of indices into the ALPHABET string that are not in the list passed as a parameter

func GetBlocks

func GetBlocks(ilist []int) <-chan Block

GetBlocks is a generator that will take a list of indices and yield pairs of (first, last) indices of sublists that are consecutive integers. For example:

ilist = [3, 2, 3, 4, 5, 1, 1, 2, 3] yields 4 pairs: (3, 3) (2, 5) - 2 through 5 (1, 1) (1, 3) - 1 through 3

Call it like this:

 c := GetBlocks(ilist) 	// c is the channel
 for pair := range c {	// but you only need to use range

	   first := pair.First
	   last := pair.Last
	   ...
	}

func GetPattern

func GetPattern(ilist []int) string

GetPattern creates part of a regular expression string that will go between brackets. For example, if the input list is []int{2, 3, 4, 5, 25}, it will return "C-DF"

func GetRegexp

func GetRegexp(letters string) string

GetRegexp will return a regular expression representing the list of letters

func IsComplete

func IsComplete(text string) bool

IsComplete scans the text and returns true if it contains no blanks.

func PointSetsEqual

func PointSetsEqual(set1, set2 []Point) bool

PointSetsEqual is true if the two sets of points are the same when considered without regard to order.

func PointsEqual

func PointsEqual(list1, list2 []Point) bool

PointsEqual is true if two lists of points are the same.

Types

type AcrossWord

type AcrossWord struct {
	WordStruct
}

func NewAcrossWord

func NewAcrossWord(number int, length int, clue string) *AcrossWord

NewAcrossWord creates a new across word.

type Block

type Block struct {
	First int
	Last  int
}

Used by GetBlocks

type Direction

type Direction string
const (
	Across Direction = "across"
	Down   Direction = "down"
)

type DownWord

type DownWord struct {
	WordStruct
}

func NewDownWord

func NewDownWord(number int, length int, clue string) *DownWord

NewDownWord creates a new across word.

type Grid

type Grid struct {
	// contains filtered or unexported fields
}

Grid contains the cells of a puzzle.

A grid is constructed with the single parameter n, which is the size (n x n) of the grid. From this, the constructor creates all the cells in the grid.

Any of the cells in the grid can be "black cells", which act as the boundaries of where the words can go. The model automatically takes care of matching a black cell with its symmetric twin 180 degrees from it.

Wherever an across or down word starts, the grid assigns the next available word number to the cell and keeps track of the lengths of the across and down words.

Grid supports a full "undo/redo" capability for as long as it exists. Any black cell additions or deletions are pushed on an undo stack.

func NewGrid

func NewGrid(n int) Grid

NewGrid creates a new Grid of the specified size. All cells are initialized to empty.

func (*Grid) AcrossLength

func (self *Grid) AcrossLength(r, c int) int

AcrossLength returns the length of the across word starting at this (r, c)

func (*Grid) AcrossWords

func (self *Grid) AcrossWords() []*AcrossWord

AcrossWords returns a slice of pointers to each of the across words in this grid.

func (*Grid) AddBlackCell

func (self *Grid) AddBlackCell(point Point)

AddBlackCell marks cell (r, c) as black (also its symmetric twin). This invalidates the word numbers so that they can be recalculated the next time GetWordNumbers() is called

func (*Grid) BlackCells

func (self *Grid) BlackCells() []Point

BlackCells returns a slice of all black cells.

func (*Grid) CalculateWordNumbers added in v0.4.0

func (self *Grid) CalculateWordNumbers()

CalculateWordNumbers figures out the numbering of the across and down words in this word based on the locations of all the black cells.

Algorithm:

  • Iterate through all cells by row and column numbers (1, 2, ... n).
  • For each r, c:
  • Ignore black cells.
  • See if this is the beginning of an across word. If so, find the row and column of the stopping point, which is either the next black cell or the edge of the puzzle.
  • Do the same for down words
  • If either an across or down word is found:
  • Create a new WordNumber with the next available number
  • Add it to the list

func (*Grid) CellValue

func (self *Grid) CellValue(point Point) string

CellValue returns the string value of the cell at this point.

func (*Grid) ClearUndoRedo added in v0.6.0

func (self *Grid) ClearUndoRedo()

ClearUndoRedo resets the undo and redo stack to empty

func (*Grid) DownLength

func (self *Grid) DownLength(r int, c int) int

DownLength returns the length of the down word starting at this (r, c)

func (*Grid) DownWords

func (self *Grid) DownWords() []*DownWord

DownWords returns a slice of pointers to each of the down words in this grid.

func (*Grid) Equal

func (this *Grid) Equal(that Grid) bool

Equals returns true if this grid is equal to another

func (*Grid) FromJSON

func (grid *Grid) FromJSON(jsonstr string) error

FromJSON recreates a grid from a JSON representation.

func (*Grid) IndexOfBlackCell

func (self *Grid) IndexOfBlackCell(point Point) int

IndexOfBlackCell returns the integer index of a given point in the black cell array, or -1, if not found.

func (Grid) IsBlackCell

func (self Grid) IsBlackCell(point Point) bool

IsBlackCell returns true if the specified point is a black cell.

func (*Grid) LookupWordNumber

func (self *Grid) LookupWordNumber(seq int) *WordNumber

LookupWordNumber finds the numbered cell having this sequence number, returning a pointer to the cell or nil, if not found.

func (*Grid) Redo

func (self *Grid) Redo()

Redo pops the last entry from the redo stack and applies it.

func (*Grid) RedoStackSize added in v0.2.0

func (self *Grid) RedoStackSize() int

RedoStackSize returns the number of items in the redo stack.

func (*Grid) RemoveBlackCell

func (self *Grid) RemoveBlackCell(point Point)

RemoveBlackCell marks cell (r, c) as not black (also its symmetric twin). This invalidates the numbered cells so that they can be recalculated the next time GetWordNumbers() is called

func (*Grid) SetCellValue

func (self *Grid) SetCellValue(point Point, value string)

SetCellValue sets the string value of the cell at this point.

func (Grid) Size

func (self Grid) Size() int

Size returns the size of the grid.

func (*Grid) Statistics

func (grid *Grid) Statistics() *Statistics

Statistics calculates the statistics needed for the UI.

func (*Grid) String

func (self *Grid) String() string

String returns a string representation of the cell matrix in this structure.

func (*Grid) SymmetricPoint

func (self *Grid) SymmetricPoint(point Point) Point

SymmetricPoint returns the point of the cell at 180 degrees rotation.

func (*Grid) ToJSON

func (grid *Grid) ToJSON() string

ToJSON returns the JSON string representation of the Grid

func (*Grid) Undo

func (self *Grid) Undo()

Undo pops the last entry from the undo stack and reverses it.

func (*Grid) UndoStackSize added in v0.2.0

func (self *Grid) UndoStackSize() int

UndoStackSize returns the number of items in the undo stack.

func (*Grid) ValidIndex

func (self *Grid) ValidIndex(i int) bool

ValidIndex returns true if the specified row or column is between 1 and n, inclusive.

func (*Grid) Validate

func (grid *Grid) Validate() (bool, []string)

Validate runs all four validation methods and returns a concatenated list of their error messages.

func (*Grid) ValidateDuplicateWords

func (self *Grid) ValidateDuplicateWords() []string

ValidateDuplicateWords checks whether there are any duplicate words, returning a list of error messages if so.

func (*Grid) ValidateInterlock

func (self *Grid) ValidateInterlock() []string

ValidateInterlock checks to see if there are any islands of white cells entirely enclosed by black cells. It returns a list of error messages if so.

func (*Grid) ValidateMinimumWordLength

func (self *Grid) ValidateMinimumWordLength() []string

ValidateMinimumWordLength checks to see that no words in this grid have length < 3. It returns a list of error messages if so.

func (*Grid) ValidateUncheckedSquares

func (self *Grid) ValidateUncheckedSquares() []string

ValidateUncheckedSquares checks to see if there are any cells that are only part of an across or a down word. Every cell must belong to both sets. It returns a list of error messages if not so.

func (*Grid) WordCount

func (self *Grid) WordCount() int

WordCount returns the number of words in the grid, both across and down.

func (*Grid) WordLengths added in v0.6.0

func (grid *Grid) WordLengths() []WordLengths

func (*Grid) WordNumbers

func (self *Grid) WordNumbers() []WordNumber

WordNumbers returns the list of word numbers

type PartitionNumber

type PartitionNumber Point

PartitionNumber is an alias for Point that makes the code more understandable.

type Point

type Point struct {
	Row int
	Col int
}

Point is a row and column

func (*Point) Equal

func (self *Point) Equal(other Point) bool

Equal is true if this point has the same row and column of another point.

func (*Point) FromJSON

func (self *Point) FromJSON(jsonstr string) error

func (*Point) Less

func (self *Point) Less(other Point) bool

Less is true if this point is before the other, reading left to right and top to bottom.

func (*Point) String

func (self *Point) String() string

String returns a string representation of this type

func (*Point) ToJSON

func (self *Point) ToJSON() string

type Points

type Points []Point

Slice of Points (for sort)

func (Points) Len

func (points Points) Len() int

func (Points) Less

func (points Points) Less(i, j int) bool

func (Points) Swap

func (points Points) Swap(i, j int)

type Statistics

type Statistics struct {
	Valid          bool          `json:"valid"`
	Errors         []string      `json:"errors"`
	Size           string        `json:"size"`
	WordCount      int           `json:"wordCount"`
	BlackCellCount int           `json:"blackCellCount"`
	WordLengths    []WordLengths `json:"wordLengths"`
}

Statistics is a structure that summarizes all the user-facing attributes of the grid.

func (*Statistics) CalculateWordLengths

func (p *Statistics) CalculateWordLengths(grid WordNumberer) []WordLengths

CalculateWordLengths creates the list of word lengths and the numbers of the across and down words of that length.

func (*Statistics) ToJSON

func (self *Statistics) ToJSON() string

ToJSON creates a JSON representation of this structure.

type ValidateInterlock

type ValidateInterlock struct {
	Grid
	// contains filtered or unexported fields
}

ValidateInterlock is a temporary structure used to perform the interlock validation.

func NewValidatorInterlock

func NewValidatorInterlock(grid Grid) ValidateInterlock

NewValidatorInterlock initializes a structure for testing interlock. It does the following:

  • Keep a reference to 'n'.
  • Keep a reference to the black cells.
  • Create an n x n matrix of partition numbers. A partition number is a '(row, col)' tuple that refers to the first cell in this partition. Note that this is not actually a 2D array, but a map of coordinates to partition numbers.
  • The matrix is 1-based, not 0-based ('r = 1, 2, ..., n, c = 1, 2, ..., n')
  • Set all the matrix elements to '(0, 0)' (meaning unmarked).

func (*ValidateInterlock) MarkAllPartitions

func (self *ValidateInterlock) MarkAllPartitions()

MarkAllPartitions goes through the whole matrix, top to bottom and left to right. If a cell does not yet belong to a partition (i.e., if the cell value is '(0, 0)'), it calls MarkPartition on it.

func (*ValidateInterlock) MarkPartition

func (self *ValidateInterlock) MarkPartition(r, c int, partno PartitionNumber)

MarkPartition sets the partition number of a (r, c) in the matrix, and recursively all its immediate neighbors. If

  • (r, c) is off the grid, or
  • (r, c) corresponds to a black cell, or
  • (r, c) is already marked,

then return. Otherwise:

  • Set (r, c) in the matrix to `partitionNumber`.
  • Form the set of all eight immediate neighbors of this cell.
  • Go through the set of all these neighbors, and recursively call MarkPartition on them.

func (*ValidateInterlock) Partitions

func (self *ValidateInterlock) Partitions() []PartitionNumber

Partitions returns the set of all distinct partition numbers. If the grid is well formed, there should be only one partition number.

func (ValidateInterlock) String

func (self ValidateInterlock) String() string

String returns a string representation of this structure

func (*ValidateInterlock) Validate

func (self *ValidateInterlock) Validate() []string

Validate performs the validation and returns a list of error messages. Note that this method calls all the others as needed, so this method should be the only one you need to call.

The grid should be considered valid if the error list has length zero.

type Word

type Word interface {
	Number() int
	Direction() Direction
	Length() int
	Clue() string
	Text(*Grid) string
}

type WordLengths

type WordLengths struct {
	Length int   `json:"length"`
	Across []int `json:"across"`
	Down   []int `json:"down"`
}

WordLengths represents a word length and the set of word numbers for across words and down words of that length.

type WordNumber

type WordNumber struct {
	// contains filtered or unexported fields
}

WordNumber is a data structure representing a numbered cell in a puzzle, which may be the start of either

  1. An across word
  2. A down word
  3. Both

func NewWordNumber

func NewWordNumber(point Point, number int, aLen int, dLen int) *WordNumber

NewWordNumber creates an initialized WordNumber and returns a pointer to it.

func (*WordNumber) AcrossLength

func (self *WordNumber) AcrossLength() int

AcrossLength returns the length of the across word starting in this cell.

func (*WordNumber) ContainsAcross

func (self *WordNumber) ContainsAcross(point Point) bool

ContainsAcross returns true if the specified point is contained in the across word starting at this WordNumber

func (*WordNumber) ContainsDown

func (self *WordNumber) ContainsDown(point Point) bool

ContainsDown returns true if the specified point is contained in the down word starting at this WordNumber

func (*WordNumber) DownLength

func (self *WordNumber) DownLength() int

DownLength returns the length of the across word starting in this cell.

func (*WordNumber) FromJSON

func (self *WordNumber) FromJSON(jsonstr string) error

FromJSON fills in a WordNumber object from a JSON string using a godawful finite state machine.

func (*WordNumber) Number

func (self *WordNumber) Number() int

Number returns the sequence number by which this cell is known.

func (*WordNumber) Point

func (self *WordNumber) Point() Point

Point returns the coordinates of the numbered cell.

func (*WordNumber) ToJSON

func (self *WordNumber) ToJSON() string

ToJSON creates a JSON string representation of this object.

type WordNumberer

type WordNumberer interface {
	WordNumbers() []WordNumber // Grid already implements this
	WordLengths() []WordLengths
}

WordNumberer is an interface of just that part of Grid that provides word numbers, for the use of unit tests.

type WordStruct

type WordStruct struct {
	// contains filtered or unexported fields
}

func (*WordStruct) Clue

func (self *WordStruct) Clue() string

func (*WordStruct) Direction

func (self *WordStruct) Direction() Direction

func (*WordStruct) FromJSON

func (self *WordStruct) FromJSON(jsonstr string) error

FromJSON fills in a word structure from the specified JSON string.

func (*WordStruct) Length

func (self *WordStruct) Length() int

func (*WordStruct) Number

func (self *WordStruct) Number() int

func (*WordStruct) Text

func (self *WordStruct) Text(grid *Grid) string

Text returns the word text

func (*WordStruct) ToJSON

func (self *WordStruct) ToJSON() string

ToJSON creates a JSON representation of this structure.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL