Turned pseudoku.py into a real project.
[pseudoku.git] / lib / pseudoku / grid / cellgroup.py
diff --git a/lib/pseudoku/grid/cellgroup.py b/lib/pseudoku/grid/cellgroup.py
new file mode 100644 (file)
index 0000000..863ca4e
--- /dev/null
@@ -0,0 +1,96 @@
+from __future__ import division
+
+from weakref import proxy
+
+class CellGroup(object):
+    """Represents any group of cells in a grid."""
+
+    ### Accessors
+
+    cells = []
+
+    ### Methods
+    # XXX inherited __init__
+
+    def find_value(self, value):
+        """Returns the cells that can be a specific value."""
+        possible_cells = []
+        for cell in self.cells:
+            if value in cell._values:
+                possible_cells.append(cell)
+
+        if len(possible_cells) == 0:
+            raise Exception  # XXX
+
+        return possible_cells
+
+    def resolve_uniques(self):
+        for value in xrange(self._grid._size):
+            # XXX cache values that are taken care of
+            possible_cells = self.find_value(value)
+
+            if len(possible_cells) > 1:
+                # Not unique
+                continue
+
+            target_cell = possible_cells[0]
+            if target_cell.solved:
+                # Already seen this
+                # XXX this is what cache is for
+                continue
+
+            # Only cell in the group that can be value
+            target_cell.set(value)
+
+
+class Box(CellGroup):
+    def _get_box_row(self):
+        return self._pos // self._grid._box_width
+    box_row = property(_get_box_row)
+
+    def _get_box_column(self):
+        return self._pos % self._grid._box_height
+    box_column = property(_get_box_column)
+
+    def _get_cells(self):
+        # XXX generator + docstring
+        cells = []
+        for row in xrange(self._grid._box_height):
+            for col in xrange(self._grid._box_width):
+                cell_row = row + self.box_row * self._grid._box_height
+                cell_col = col + self.box_column * self._grid._box_width
+                cells.append(self._grid.cell(cell_row, cell_col))
+        return cells
+    cells = property(_get_cells)
+
+    def __init__(self, grid, position):
+        self._grid = proxy(grid)
+        self._pos = position
+
+
+class Row(CellGroup):
+    def _get_cells(self):
+        # XXX generator + docstring
+        cells = []
+        for col in xrange(self._grid._size):
+            cells.append(self._grid.cell(self._pos, col))
+        return cells
+    cells = property(_get_cells)
+
+    def __init__(self, grid, position):
+        self._grid = proxy(grid)
+        self._pos = position
+
+
+class Column(CellGroup):
+    def _get_cells(self):
+        # XXX generator + docstring
+        cells = []
+        for row in xrange(self._grid._size):
+            cells.append(self._grid.cell(row, self._pos))
+        return cells
+    cells = property(_get_cells)
+
+    def __init__(self, grid, position):
+        self._grid = proxy(grid)
+        self._pos = position