takuzu.go
author Mikael Berthe <mikael@lilotux.net>
Sat, 07 Apr 2018 22:49:51 +0200
changeset 15 eac7d78ff641
parent 10 8dc05ff5dbe2
permissions -rw-r--r--
Update gotak import path to fix Travis build Update import path in the gotak subdir so that Travis tests can be played against the Github repository. Also, add missing dependencies to the Travis YAML file.
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
10
8dc05ff5dbe2 Add (MIT) license
Mikael Berthe <mikael@lilotux.net>
parents: 8
diff changeset
     1
// Copyright (C) 2016 Mikael Berthe <mikael@lilotux.net>. All rights reserved.
8dc05ff5dbe2 Add (MIT) license
Mikael Berthe <mikael@lilotux.net>
parents: 8
diff changeset
     2
// Use of this source code is governed by the MIT license,
8dc05ff5dbe2 Add (MIT) license
Mikael Berthe <mikael@lilotux.net>
parents: 8
diff changeset
     3
// which can be found in the LICENSE file.
8dc05ff5dbe2 Add (MIT) license
Mikael Berthe <mikael@lilotux.net>
parents: 8
diff changeset
     4
8dc05ff5dbe2 Add (MIT) license
Mikael Berthe <mikael@lilotux.net>
parents: 8
diff changeset
     5
// Package takuzu provides functions to solve, build or validate takuzu
8dc05ff5dbe2 Add (MIT) license
Mikael Berthe <mikael@lilotux.net>
parents: 8
diff changeset
     6
// puzzles.
0
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
     7
package takuzu
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
     8
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
     9
import (
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    10
	"bytes"
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    11
	"fmt"
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    12
	"math"
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    13
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    14
	"github.com/pkg/errors"
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    15
)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    16
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    17
// Cell is a single cell of a Takuzu game board
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    18
type Cell struct {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    19
	Defined bool
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    20
	Value   int
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    21
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    22
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    23
// Takuzu is a Takuzu game board (Size x Size)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    24
type Takuzu struct {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    25
	Size  int
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    26
	Board [][]Cell
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    27
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    28
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    29
// New creates a new Takuzu board
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    30
func New(size int) Takuzu {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    31
	t := Takuzu{Size: size}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    32
	t.Board = make([][]Cell, size)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    33
	for l := range t.Board {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    34
		t.Board[l] = make([]Cell, size)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    35
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    36
	return t
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    37
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    38
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    39
// NewFromString creates a new Takuzu board from a string definition
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    40
func NewFromString(s string) (*Takuzu, error) {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    41
	l := len(s)
2
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
    42
	if l < 4 {
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
    43
		return nil, errors.New("bad string length")
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
    44
	}
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
    45
0
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    46
	size := int(math.Sqrt(float64(l)))
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    47
	if size*size != l {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    48
		return nil, errors.New("bad string length")
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    49
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    50
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    51
	i := 0
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    52
	t := New(size)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    53
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    54
	for line := 0; line < size; line++ {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    55
		for col := 0; col < size; col++ {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    56
			switch s[i] {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    57
			case '0', 'O':
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    58
				t.Board[line][col].Defined = true
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    59
				t.Board[line][col].Value = 0
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    60
			case '1', 'I':
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    61
				t.Board[line][col].Defined = true
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    62
				t.Board[line][col].Value = 1
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    63
			case '.':
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    64
			default:
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    65
				return nil, errors.New("invalid char in string")
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    66
			}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    67
			i++
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    68
		}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    69
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    70
	return &t, nil
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    71
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    72
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    73
// ToString converts a takuzu board to its string representation
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    74
func (b Takuzu) ToString() string {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    75
	var sbuf bytes.Buffer
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    76
	for line := 0; line < b.Size; line++ {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    77
		for col := 0; col < b.Size; col++ {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    78
			if b.Board[line][col].Defined {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    79
				sbuf.WriteString(fmt.Sprintf("%d", b.Board[line][col].Value))
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    80
				continue
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    81
			}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    82
			sbuf.WriteByte('.')
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    83
		}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    84
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    85
	return sbuf.String()
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    86
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    87
6
110d38ae22cd Refactor code; split takuzu.go and create solve.go
Mikael Berthe <mikael@lilotux.net>
parents: 4
diff changeset
    88
// DumpString writes the content of the board as a string
0
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    89
func (b Takuzu) DumpString() {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    90
	fmt.Println(b.ToString())
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    91
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    92
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    93
// Clone returns a copy of the Takuzu board
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    94
func (b Takuzu) Clone() Takuzu {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    95
	c := New(b.Size)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    96
	for line := range b.Board {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    97
		for col := range b.Board[line] {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    98
			c.Board[line][col] = b.Board[line][col]
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
    99
		}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   100
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   101
	return c
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   102
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   103
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   104
// Copy copies a Takuzu board to another existing board
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   105
func Copy(src, dst *Takuzu) error {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   106
	if src.Size != dst.Size {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   107
		return errors.New("sizes do not match")
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   108
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   109
	for line := range src.Board {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   110
		for col := range src.Board[line] {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   111
			dst.Board[line][col] = src.Board[line][col]
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   112
		}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   113
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   114
	return nil
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   115
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   116
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   117
// BoardsMatch compares a Takuzu board to another, optionally ignoring
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   118
// empty cells.  Returns true if the two boards match.
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   119
func BoardsMatch(t1, t2 *Takuzu, ignoreUndefined bool) (match bool, line, col int) {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   120
	match = true
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   121
2
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
   122
	if t1 == nil || t2 == nil {
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
   123
		line, col = -1, -1
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
   124
		match = false
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
   125
		return
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
   126
	}
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
   127
0
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   128
	if t1.Size != t2.Size {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   129
		line, col = -1, -1
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   130
		match = false
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   131
		return
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   132
	}
2
d41c4f8fe066 Add some checks
Mikael Berthe <mikael@lilotux.net>
parents: 0
diff changeset
   133
0
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   134
	for line = range t1.Board {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   135
		for col = range t1.Board[line] {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   136
			if !t1.Board[line][col].Defined || !t2.Board[line][col].Defined {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   137
				// At least one of the cells is empty
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   138
				if ignoreUndefined ||
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   139
					!(t1.Board[line][col].Defined || t2.Board[line][col].Defined) {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   140
					// Both cells are empty or we ignore empty cells
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   141
					continue
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   142
				}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   143
				match = false
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   144
				return
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   145
			}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   146
			// Both cells are defined
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   147
			if t1.Board[line][col].Value != t2.Board[line][col].Value {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   148
				match = false
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   149
				return
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   150
			}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   151
		}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   152
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   153
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   154
	line, col = -1, -1
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   155
	return
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   156
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   157
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   158
// Set sets the value of the cell; a value -1 will set the cell as undefined
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   159
func (c *Cell) Set(value int) {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   160
	if value != 0 && value != 1 {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   161
		c.Defined = false
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   162
		return
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   163
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   164
	c.Defined = true
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   165
	c.Value = value
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   166
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   167
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   168
// Set sets the value of a specific cell
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   169
// A value -1 will undefine the cell
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   170
func (b Takuzu) Set(l, c, value int) {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   171
	if value != 0 && value != 1 {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   172
		b.Board[l][c].Defined = false
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   173
		return
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   174
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   175
	b.Board[l][c].Defined = true
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   176
	b.Board[l][c].Value = value
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   177
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   178
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   179
// GetLine returns a slice of cells containing the ith line of the board
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   180
func (b Takuzu) GetLine(i int) []Cell {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   181
	return b.Board[i]
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   182
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   183
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   184
// GetColumn returns a slice of cells containing the ith column of the board
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   185
func (b Takuzu) GetColumn(i int) []Cell {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   186
	c := make([]Cell, b.Size)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   187
	for l := range b.Board {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   188
		c[l] = b.Board[l][i]
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   189
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   190
	return c
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   191
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   192
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   193
// GetLinePointers returns a slice of pointers to the cells of the ith line of the board
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   194
func (b Takuzu) GetLinePointers(i int) []*Cell {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   195
	r := make([]*Cell, b.Size)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   196
	for l := range b.Board[i] {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   197
		r[l] = &b.Board[i][l]
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   198
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   199
	return r
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   200
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   201
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   202
// GetColumnPointers returns a slice of pointers to the cells of the ith column of the board
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   203
func (b Takuzu) GetColumnPointers(i int) []*Cell {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   204
	r := make([]*Cell, b.Size)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   205
	for l := range b.Board {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   206
		r[l] = &b.Board[l][i]
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   207
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   208
	return r
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   209
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   210
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   211
// FillLineColumn add missing 0s or 1s if all 1s or 0s are there.
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   212
// Note: This method can update b.
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   213
func (b Takuzu) FillLineColumn(l, c int) {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   214
	fillRange := func(r []*Cell) {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   215
		size := len(r)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   216
		var notFull bool
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   217
		var n [2]int
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   218
		for x := 0; x < size; x++ {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   219
			if r[x].Defined {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   220
				n[r[x].Value]++
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   221
			} else {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   222
				notFull = true
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   223
			}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   224
		}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   225
		if !notFull {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   226
			return
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   227
		}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   228
		if n[0] == size/2 {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   229
			// Let's fill the 1s
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   230
			for _, x := range r {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   231
				if !x.Defined {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   232
					x.Defined = true
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   233
					x.Value = 1
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   234
				}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   235
			}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   236
		} else if n[1] == size/2 {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   237
			// Let's fill the 0s
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   238
			for _, x := range r {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   239
				if !x.Defined {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   240
					x.Defined = true
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   241
					x.Value = 0
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   242
				}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   243
			}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   244
		}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   245
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   246
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   247
	var cells []*Cell
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   248
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   249
	// Fill line
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   250
	cells = b.GetLinePointers(l)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   251
	fillRange(cells)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   252
	// Fill column
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   253
	cells = b.GetColumnPointers(c)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   254
	fillRange(cells)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   255
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   256
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   257
// DumpBoard displays the Takuzu board
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   258
func (b Takuzu) DumpBoard() {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   259
	fmt.Println()
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   260
	for i := range b.Board {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   261
		dumpRange(b.Board[i])
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   262
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   263
}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   264
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   265
func dumpRange(cells []Cell) {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   266
	for _, c := range cells {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   267
		if !c.Defined {
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   268
			fmt.Printf(". ")
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   269
			continue
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   270
		}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   271
		fmt.Printf("%d ", c.Value)
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   272
	}
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   273
	fmt.Println()
00371339bbcc Import refactored version
Mikael Berthe <mikael@lilotux.net>
parents:
diff changeset
   274
}