initField();
$this->emptyTarget = array(0,0,0,0,0,0,0,0,0,0);
}
//das Feld vorbereiten
public function initField()
{
for($i=0;$i<9;$i++)
{
for($j=0;$j<9;$j++)
{
$this->field[$i][$j]=0;
}
}
}
//das Feld ausgeben
public function printField()
{
for($i=0;$i<9;$i++)
{
if($i%3==0 AND $i>0)
{
echo "
-------------
";
}
else
{
echo "
";
} for($j=0;$j<9;$j++)
{
if($j%3==0 AND $j>0)
{
echo "|";
}
echo $this->field[$i][$j];
}
}
}
//ein Demo-Feld anlegen
// - diese Sudokus kommen von: www.einsamehunde.de bzw www.a-tempo.de
public function initDemoField()
{
// //Quelle: http://www.a-tempo.de/sudoku/Sudoku092007.pdf
// $this->field=array(
// array(0,0,0,1,0,0,0,0,4),
// array(0,0,8,0,0,4,9,2,0),
// array(0,1,0,8,0,3,5,7,0),
// array(2,0,7,0,0,0,1,6,0),
// array(0,0,0,0,0,0,0,0,0),
// array(0,4,9,0,0,0,8,0,3),
// array(0,3,5,7,0,2,0,9,0),
// array(0,8,1,6,0,0,2,0,0),
// array(7,0,0,0,0,9,0,0,0)
// );
$this->field=array(
array(0,0,2,0,3,0,0,1,0),
array(0,7,0,0,0,0,0,0,5),
array(0,0,3,5,0,2,0,0,0),
array(6,0,0,9,0,4,1,0,0),
array(1,0,0,0,2,0,0,0,8),
array(0,0,7,3,0,6,0,0,2),
array(0,0,0,8,0,9,3,0,0),
array(7,0,0,0,0,0,0,6,0),
array(0,4,0,0,7,0,5,0,0)
);
}
public function createTarget()
{
return array(0,1,1,1,1,1,1,1,1,1);
}
//Testfunktion um sich die Zwischenergebnisse anzuschauen
public function printTarget($target)
{
foreach($target as $k => $v)
{
if($v==1)
{
$buffer .= $k.",";
}
}
$buffer=substr($buffer,0,-1);
echo $buffer;
}
// Prüft, ob anhand der Zeile bestimmt werden kann, welche Zahl es ist
// Gibt ein Array mit möglichen Zahlen zurück
// Parameter target kann als Vorauswahl übergeben werden
public function checkRow($x,$y,$target=NULL)
{
if(!$target)
{
$target=$this->createTarget();
}
//nur bearbeiten, wenn das Feld noch leer ist!
if($this->field[$x][$y]==0)
{
for($i=0;$i<9;$i++)
{
$target[$this->field[$x][$i]]=0;
}
}
else
{
return $this->emptyTarget;
}
return $target;
}
// Prüft, ob anhand der Spalte bestimmt werden kann, welche Zahl es ist
// Gibt ein Array mit möglichen Zahlen zurück
// Parameter target kann als Vorauswahl übergeben werden
public function checkCol($x,$y,$target=NULL)
{
if(!$target)
{
$target=$this->createTarget();
}
//nur bearbeiten, wenn das Feld noch leer ist!
if($this->field[$x][$y]==0)
{
for($i=0;$i<9;$i++)
{
$target[$this->field[$i][$y]]=0;
}
}
else
{
return $this->emptyTarget;
}
return $target;
}
// Prüft, ob anhand des aktuellen Unter-Feldes bestimmt werden kann, welche Zahl es ist
// Gibt ein Array mit möglichen Zahlen zurück
// Parameter target kann als Vorauswahl übergeben werden
public function checkField($x,$y,$target=NULL)
{
if(!$target)
{
$target=$this->createTarget();
}
//nur bearbeiten, wenn das Feld noch leer ist!
if($this->field[$x][$y]==0)
{
$a = $x - ($x % 3);
$a3 = $a+3;
$b = $y - ($y % 3);
$b3 = $b+3;
for($i=$a;$i<$a3;$i++)
{
for($j=$b;$j<$b3;$j++)
{
$target[$this->field[$i][$j]]=0;
}
}
}
else
{
return $this->emptyTarget;
}
return $target;
}
//ruft die drei negativen Check-Funktionen nacheinander auf
public function checkItem($x,$y)
{
$target = $this->checkRow($x,$y);
$target = $this->checkCol($x,$y,$target);
$target = $this->checkField($x,$y,$target);
return $target;
}
// Checkt das komplette Sudoku-Feld ab; gibt zurück ob ein Fortschritt erzielt werden konnte
public function processSudoku_negative()
{
$delta=0; #Fortschrittsprüfer => wenn es so nicht mehr weitergeht, abbrechen!
for($i=0;$i<9;$i++)
{
for($j=0;$j<9;$j++)
{
$target = $this->checkItem($i,$j);
if($this->checkTarget($target))
{
$this->updateField($i,$j,$target);
$delta++;
}
}
}
return $delta;
}
//prüfe, ob das Target nur noch genau einen Wert enthält
public function checkTarget($target)
{
$count=0;
foreach($target as $k => $v)
{
$count+=$v;
}
if($count==1)
{
return true;
}
else
{
return false;
}
}
//einen gefundenen Wert in das Feld eintragen
public function updateField($x,$y,$target)
{
//hier Sanity-Check einbauen!
$this->field[$x][$y]=$this->getTargetValue($target);
}
//Wenn das target nur noch einen Wert enthält, diesen zurückgeben
public function getTargetValue($target)
{
if($this->checkTarget($target))
{
foreach($target as $k => $v)
{
if($v==1)
{
return $k;
}
}
}
return 0;
}
//Prüft, ob das Feld vollständig ausgefüllt wurde, also gelöst ist
public function isSolved()
{
for($i=0;$i<9;$i++)
{
for($j=0;$j<9;$j++)
{
if($this->field[$i][$j]==0)
{
return false;
}
}
}
return true;
}
}
?>