sign in | join about | help | sitemap
Connecting Tech Pros Worldwide
Thekid's Avatar

line print out for sudoku solver


Question posted by: Thekid (Member) on October 1st, 2008 01:11 AM
Hi, I found this sudoku solver online and it works good but I was wondering how I could get the answer that's in matrix form, to also print out in a single comma-delimited line, instead of 9 rows of 9?

Expand|Select|Wrap|Line Numbers
  1. from copy import deepcopy
  2. class DeadEnd(Exception): pass
  3.  
  4.  
  5. class Matrix:
  6.     def __init__(self, input):
  7.         self.rows = [[] for i in range(9)]
  8.         self.cols  = [[] for i in range(9)]
  9.         self.submatrices = [[] for i in range(9)]
  10.         self.cells = [Cell(i,self) for i in range(81)]
  11.         self.subdiagonals = [self.rows[i][j+i%3] for i in range(9) for j in [0,3,6]]
  12.         input = [s not in '-*' and int(s) or 0 for s in input if s in '0123456789-*']
  13.         for cell,val in zip(self.cells, input): 
  14.             if val: cell.setSolution(val)
  15.  
  16.     def solve(self): #Brute-force solver
  17.         self.solveByReduction()
  18.         lensols=[(len(c.solutions),c.index) for c in self.cells if not c.solved]
  19.         if not lensols: return True
  20.         unsolved = min(lensols)[1]
  21.         solutions = list(self.cells[unsolved].solutions)
  22.         for s in solutions:
  23.             tmpmatrix = deepcopy(self)
  24.             try:
  25.                 tmpmatrix.cells[unsolved].setSolution(s)
  26.                 if tmpmatrix.solve():
  27.                     self.update(tmpmatrix)
  28.                     return True
  29.             except DeadEnd: pass
  30.  
  31.     def solveByReduction(self):
  32.         while True:
  33.             self.changed = False
  34.             for c in self.cells: c.solve()
  35.             for c in self.subdiagonals: c.skim()
  36.             if not self.changed: break
  37.  
  38.     def update(self, m):
  39.         self.rows, self.cols, self.submatrices, self.cells, self.subdiagonals=\
  40.             m.rows, m.cols, m.submatrices, m.cells, m.subdiagonals
  41.  
  42.     def __str__(self):
  43.         return "\n".join(str([c for c in row ])[1:-1] for row in self.rows)
  44.  
  45.  
  46. class Cell:
  47.     def __init__(self, index, matrix):
  48.         self.solved = False
  49.         self.matrix = matrix
  50.         self.index = index
  51.         self.row = matrix.rows[index/9]
  52.         self.col = matrix.cols[index%9]
  53.         self.submatrix = matrix.submatrices[((index/9)/3)*3+(index%9)/3]
  54.         self.row.append(self)
  55.         self.col.append(self)
  56.         self.submatrix.append(self)
  57.         self.solutions = set(range(1,10))
  58.  
  59.     def solve(self):
  60.         if self.solved: return
  61.         if len(self.solutions) == 1:
  62.             self.setSolution(self.solutions.pop())
  63.         else:
  64.             sol = set()
  65.             for cells in [self.row, self.col, self.submatrix]:
  66.                 otherSolutions = self.cells2sols(cells, self)
  67.                 sol |= (self.solutions - otherSolutions)
  68.             if len(sol) > 1: raise DeadEnd()
  69.             if sol: self.setSolution(sol.pop())
  70.  
  71.     def skim(self):
  72.         submatrix = set(self.submatrix)
  73.         for r in  (set(self.row), set(self.col)):
  74.             subset1 = submatrix - r
  75.             subset2 = r - submatrix
  76.             solsNotIn1 = set(range(1,10)) - self.cells2sols(subset2)
  77.             solsNotIn2 = set(range(1,10)) - self.cells2sols(subset1)
  78.             for c in subset1: c.delSolutions(solsNotIn1)
  79.             for c in subset2: c.delSolutions(solsNotIn2)
  80.  
  81.     def setSolution(self, val):
  82.         self.solved = True
  83.         self.solutions = set((val,))
  84.         self.matrix.changed = True
  85.         for other in self.row+self.col+self.submatrix:
  86.             if other is self: continue
  87.             if other.solutions == self.solutions: raise DeadEnd()
  88.             other.delSolutions(self.solutions)
  89.  
  90.     def delSolutions(self, val):
  91.         if not self.solved and val & self.solutions:
  92.             self.solutions -= val
  93.             self.matrix.changed = True
  94.             if not self.solutions: raise DeadEnd()
  95.  
  96.     def __repr__(self):
  97.         return str(self.solved and list(self.solutions)[0] or list(self.solutions))
  98.  
  99.     @staticmethod
  100.     def cells2sols(cells, exclude=None):
  101.         return set(s for c in cells for s in c.solutions if c is not exclude)
  102.  
  103.  
  104. if __name__ == "__main__":
  105.     input = '''5,6,7,2,3,0,0,0,1,2,0,0,0,9,1,5,6,7,8,0,1,0,0,0  ,2,0,4,0,5,0,1,2,0,7,8,9,0,2,3,0,0,0,0,5,0,0,8,9,0  ,5,6,0,2,3,0,7,0,3,4,5,0,1,2,3,0,5,9,1,2,0,7,8,9,0  ,2,6,7,8,3,4,5'''
  106.     matrix = Matrix(input)
  107.     matrix.solve()
  108.     print matrix
  109.  
1 Answer Posted
kaarthikeyapreyan's Avatar
kaarthikeyapreyan October 3rd, 2008 06:29 AM
Member - 74 Posts
#2: Re: line print out for sudoku solver

Hey use the numarray or numpy to print the output in an array form
Reply
Not the answer you were looking for? Post your question . . .
197,013 members ready to help you find a solution.
Join Bytes.com

What is Bytes?

We are a network of experts and professionals in IT and software development that help one another with answers to tough questions and share insights. Get the best answers to your questions from over 197,013 network members.
Post your question now . . .
It's fast and it's free

Popular Articles

Top Python Contributors