<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet href="#SudokuStyle" type="text/css"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<title>Sudokiller - A JavaScript SuDoku Solver</title>
<style type="text/css" id="SudokuStyle">
p { text-align: center; }
table { border: 1px solid #000; border-collapse: collapse;
margin-left: auto; margin-right: auto; }
input { border: 1px solid #ccc; }
</style>
<script type="text/Javascript">
/************************************************************************
*
* sudokiller.js - Javascript SuDoku solver (see it in action!)
*
* Author: Daniele Mazzocchio
* Last update: Jan 30, 2006
*
* Download sources
************************************************************************/
function SudoKiller() {
/*
* Constructor of the SuDoku solver.
*/
BOARD_SIZE = 9; // Width and height of the SuDoku board
BOX_SIZE = 3; // Width and height of the inner boxes
EMPTY = ""; // Empty cell marker
var board = new Array(); // Cells array
function check(num, row, col) {
/*
* Check if num is, according to SuDoku rules, a legal candidate
* for the given cell.
*/
var row_index, col_index, box_index; // Indexes of the cells to check
var r = (Math.floor(row / BOX_SIZE) * BOX_SIZE);
var c = (Math.floor(col / BOX_SIZE) * BOX_SIZE);
for (var i=0; i<BOARD_SIZE; i++) {
row_index = (row * BOARD_SIZE) + i;
col_index = col + (i * BOARD_SIZE);
box_index = (r + Math.floor(i / BOX_SIZE)) * BOARD_SIZE + c + (i % BOX_SIZE);
if (num == board[row_index].value ||
num == board[col_index].value ||
num == board[box_index].value)
return false;
}
return true;
}
function guess(index) {
/*
* Recursively test all candidate numbers for a given cell until
* the board is complete.
*/
var row = Math.floor(index / BOARD_SIZE);
var col = index % BOARD_SIZE;
if (index >= board.length)
return true;
if (board[index].value != EMPTY)
return guess(index + 1);
for (var i=1; i<=BOARD_SIZE; i++) {
if (check(i, row, col)) {
board[index].value = i;
if (guess(index + 1))
return true;
}
}
board[index].value = EMPTY;
return false;
}
this.kill = function() {
/*
* Get the board content and start solving the game.
*/
board = document.getElementsByTagName("input");
if (!guess(0))
alert("Sorry, solution not found!");
}
}
SudoKiller.prototype.drawBoard = function() {
/*
* Draw the game board.
*/
var hstyle, vstyle; // Borders styles
for (var row=0; row<BOARD_SIZE; row++) {
document.write('<tr>');
hstyle = row % BOX_SIZE ? "" : "border-top: 1px solid #000;";
for (var col=0; col<BOARD_SIZE; col++) {
vstyle = col % BOX_SIZE ? "" : "border-left: 1px solid #000;";
document.write('<td style="' + hstyle + vstyle + '">');
document.write('<input type="text" size="1" maxlength="1" /></td>');
}
document.write('</tr>');
}
}
</script>
</head>
<body>
<p>Fill the SuDoku board with the puzzle you want to solve and press the "Kill!" button.</p>
<table>
<script type="text/javascript">
var sk = new SudoKiller();
sk.drawBoard();
</script>
</table>
<p><button type="button" onclick="sk.kill();">Kill!</button></p>
</body>
</html>