Example #1
0
/** Fill the stack with empty cells. */
static void GridFillStackWithEmptyCells(void)
{
	int Row, Column;
	
	CellsStackInitialize();
	
	// Reverse parsing to create a stack with empty coordinates beginning on the top-left part of the grid (this allows to make speed comparisons with the older way to find empty cells)
	for (Row = Grid_Size - 1; Row >= 0; Row--)
	{
		for (Column = Grid_Size - 1; Column >= 0; Column--)
		{
			if (Grid[Row][Column] == GRID_EMPTY_CELL_VALUE) CellsStackPush(Row, Column);
		}
	}
}
Example #2
0
/** The brute force backtrack algorithm.
 * @return 1 if the grid was solved or 0 if not.
 */
static int Backtrack(void)
{
	int Row, Column;
	unsigned int Bitmask_Missing_Numbers, Tested_Number;
	
	// Find the first empty cell (don't remove the stack top now as the backtrack can return soon if no available number is found) 
	if (CellsStackReadTop(&Row, &Column) == 0)
	{
		// No empty cell remain and there is no error in the grid : the solution has been found
		if (GridIsCorrectlyFilled()) return 1;
		
		// A bad grid was generated...
		#ifdef DEBUG
			printf("[Backtrack] Bad grid generated !\n");
		#endif
		return 0;
	}
	
	// Get available numbers for this cell
	Bitmask_Missing_Numbers = GridGetCellMissingNumbers(Row, Column);
	// If no number is available a bad grid has been generated... It's safe to return here as the top of the stack has not been altered
	if (Bitmask_Missing_Numbers == 0) return 0;
	
	#ifdef DEBUG
		printf("[Backtrack] Available numbers for (row %d ; column %d) : ", Row, Column);
		GridShowBitmask(Bitmask_Missing_Numbers);
	#endif
	
	// Try each available number
	for (Tested_Number = 0; Tested_Number < Grid_Size; Tested_Number++)
	{
		// Loop until an available number is found
		if (!(Bitmask_Missing_Numbers & (1 << Tested_Number)))
		{
			Avoided_Bad_Solutions_Count++;
			continue;
		}
		
		// Try the number
		GridSetCellValue(Row, Column, Tested_Number);
		GridRemoveCellMissingNumber(Row, Column, Tested_Number);
		CellsStackRemoveTop(); // Really try to fill this cell, removing it for next simulation step
		Loops_Count++;
		
		#ifdef DEBUG
			printf("[Backtrack] Modified grid :\n");
			GridShowDifferences(GRID_COLOR_CODE_BLUE);
			putchar('\n');
		#endif

		// Simulate next state
		if (Backtrack() == 1) return 1; // Good solution found, go to tree root
		
		// Bad solution found, restore old value
		GridSetCellValue(Row, Column, GRID_EMPTY_CELL_VALUE);
		GridRestoreCellMissingNumber(Row, Column, Tested_Number);
		CellsStackPush(Row, Column); // The cell is available again
		Bad_Solutions_Found_Count++;
		
		#ifdef DEBUG
			printf("[Backtrack] Restored grid :\n");
			GridShowDifferences(GRID_COLOR_CODE_RED);
			putchar('\n');
		#endif
	}
	// All numbers were tested unsuccessfully, go back into the tree
	return 0;
}