To prove that the program works, it is sufficient to print the solution or solutions in plain text. However, the author also envisions use of this script as a flashy GUI demo that shows the program's steps in solving the puzzle as it performs them.
Consequently, the solution will be divided into three major components:
A module named sudosolver.py will encapsulate all the
mechanics of solving the puzzle, but will not have any
specific mechanism for input or output.
A simple script named sudoku will use that module to find the solutions, and print them in plain-text format.
A GUI-based script named sudogui will use the sudosolver.py
module to display each solution graphically as the
solver works on it, writing digits on the display when
the program tries a step of the solution, and then
erasing digits if they prove to be unworkable.
Clearly, the sudosolver.py module cannot do any output, since it
doesn't know whether its output will go to a regular file
stream or to a GUI. However, this module can't just return
a solution when it gets one, because there may be multiple
solutions. Also, how is it to handle the requirement that
the GUI be notified to update its display whenever any
digit in the puzzle gets placed or removed?
The solution is to use callbacks—that is, the module should be able to call a procedure outside itself to report solutions or state changes. This is a good example of the Observer pattern discussed in the classic work Design Patterns by Gamma et al. (ISBN 0-201-63361-2).
The sudosolver.py module contains a class named SudokuSolver that
encapsulates the puzzle-solving logic. This class has two
Observer callbacks; this allows us to decouple the
input/output considerations from the logic.
One Observer is called whenever a solution is found.
Another, optional Observer is called whenever the puzzle's state changes.