我正在尝试准备一个数独项目。我现在有行和列控件。 如果我在运行时创建一个数组9 * 9程序崩溃并且窗体窗口冻结。我点击"停止调试"停止它。按钮。但它适用于小阵列。例如3 * 3。如果我创建6 * 6,有时更多,有时无效。但到目前为止,9 * 9我无法取得成功。
问题是什么,你对这个问题有什么看法吗? 我是编程新手。如果你用一些例子写下答案,我会很高兴。
提前致谢..
只是代码的一部分。我用英语改变了变量..
public bool rowControl(int[,] sudoku, int row, int value)
{
for (int i = 0; i < 9; i++)
{
if (sudoku[row, i] == value)
{
return false;
}
}
return true;
}
public bool columnControl(int[,] sudoku, int column, int value)
{
for (int i = 0; i < 9; i++)
{
if (sudoku[i, column == value)
{
return false;
}
}
return true;
}
private void button1_Click(object sender, EventArgs e)
{
for (int f = 0; f < 9; f++)
{
for (int i = 0; i < 9; i++)
{
while (rowControl(sudokuArr, f, random) == false || columnControl(sudokuArr, i, random) == false)
{
random= r.Next(1, 10);
}
sudokuArr[f, i] = random;
}
}
}
答案 0 :(得分:0)
好的,我不知道你的原始问题是什么,但修改后的问题是递归调用BSudoku
,直到你遇到StackOverflow错误。这段代码作品:
namespace Sudoku
{
public partial class Form1 : Form
{
static TextBox[,] graphicSudokuBoard;
int[,] field = new int[9, 9];
public void CreateSudokuBoard()
{
int x = 10, y = 10;
int tabIndex = 0, textBoxHeight = 0;
graphicSudokuBoard = new TextBox[9, 9];
for (int row = 0; row < 9; row++)
{
x = 10;
for (int col = 0; col < 9; col++)
{
TextBox textBox = new TextBox();
textBox.BorderStyle = BorderStyle.FixedSingle;
textBox.Font = new Font(textBox.Font.FontFamily, 24F, FontStyle.Bold);
textBox.MaxLength = 1;
textBox.TextAlign = HorizontalAlignment.Center;
textBox.Width = textBox.Height;
textBox.TabIndex = tabIndex++;
textBox.Location = new Point(x, y);
this.Controls.Add(textBox);
graphicSudokuBoard[row, col] = textBox;
textBoxHeight = textBox.Height;
x += textBox.Width - 1;
if (col % 3 == 2)
x++;
}
y += textBoxHeight - 1;
if (row % 3 == 2)
y++;
}
}
bool chkRow(int row, int value, int[,] arr)
{
for (int i = 0; i < 9; i++)
{
if (arr[row, i] == value)
{
return false;
}
}
return true;
}
bool chkColumn(int column, int value, int[,] arr)
{
for (int i = 0; i < 9; i++)
{
if (arr[i, column] == value)
{
return false;
}
}
return true;
}
bool chkSquare(int row, int column, int value, int[,] arr)
{
for (int i = 0; i < 3; i++)
{
for (int j = 0; j < 3; j++)
{
if (arr[row - (row % 3) + i, column - (column % 3) + j] == value)
{
return false;
}
}
}
return true;
}
bool chkAll(int row, int column, int value, ref int[,] arr)
{
if (!chkRow(row, value, arr))
return false;
if (!chkColumn(column, value, arr))
return false;
if (!chkSquare(row, column, value, arr))
return false;
return true;
}
int[,] BSudoku(int value, int px, int py, int[,] field)
{
int[,] sudokuCells = new int[9, 9];
for (int i = 0; i < 9; i++)
{
for (int j = 0; j < 9; j++)
{
sudokuCells[j, i] = field[j, i];
}
}
for (int x = px; x < 9; x++)
{
for (int y = py; y < 9; y++)
{
if (sudokuCells[x, y] == 0)
{
for (int val = 1; val <= 9; val++)
{
if (val == 9 && !chkAll(x, y, val, ref sudokuCells))
{
sudokuCells[x, y] = 0;
if (x > 0 || y > 0)
{
if (x > 0 && y == 0)
{
x--;
y = 8;
}
else y--;
}
while(sudokuCells[x,y] == 9)
{
sudokuCells[x, y] = 0;
if (x > 0 || y > 0)
{
if (x > 0 && y == 0)
{
x--;
y = 8;
}
else y--;
}
}
sudokuCells[x, y]++;
}
if (chkAll(x, y, val, ref sudokuCells))
{
sudokuCells[x, y] = val;
graphicSudokuBoard[x, y].Text = sudokuCells[x, y].ToString();
break;
}
}
}
}
}
for (int i = 0; i < 9; i++)
{
for (int j = 0; j < 9; j++)
{
graphicSudokuBoard[j, i].Text = sudokuCells[j, i].ToString();
}
}
//MessageBox.Show("Done!");
return sudokuCells;
}
private void button1_Click(object sender, EventArgs e)
{
for (int i = 0; i < 9; i++)
{
for (int j = 0; j < 9; j++)
{
string s = graphicSudokuBoard[i, j].Text;
if (s == "") s = "0";
field[i, j] = Convert.ToInt32(s);
}
}
BSudoku(0, 0, 0, field);
}
public Form1()
{
InitializeComponent();
CreateSudokuBoard();
}
}
}
我必须纠正许多问题。一,你的chk___
函数不能是静态的。这将永远不会让你的循环变量一旦返回就重新开始。我不记得我修复的所有内容,但作为警告,大多数SO人都不会花时间来检查你的代码。上面的代码解决了StackOverflow问题以及许多其他问题。如果使用足够的值对其进行播种,它将返回正确的函数,但是仍然存在一些问题,它允许多个值在行,列和方形中。另外,您可能希望使用ref
关键字将数组作为参考传递;这将通过一个很好的协议加快您的代码。作为最后一个警告,因为这是一个蛮力解算器,你需要为它设置几个值,以便它运行得相当快。当我为我填充三行时它会很快,但会产生不正确的结果。你应该能够解决这个问题,我没有时间弄清楚现在发生了什么。