数独求解器出现Abort Trap Error:6错误,请求排查原因
兄弟,你的数独回溯求解器这俩问题——先错误输出No Solution再触发Abort Trap:6——大概率真的是行列递增逻辑出了问题,而且这俩问题是连锁的!咱们一步步拆解:
先搞懂Abort Trap:6的根源
这个错误在C/C++这类底层语言里,最常见的原因就是数组越界访问——你的代码访问了二维网格不存在的索引(比如grid[9][x],毕竟数独行列索引是0-8)。结合你说的行列初始参数是0,十有八九是行列递增到边界后没处理好,直接越界踩内存了。
为什么会提前输出No Solution?
你的测试用例是有解的,程序却返回无解,说明行列遍历逻辑提前终止了递归,没走完整个网格就错误返回了FALSE。常见坑点:
- 列递增到9时,没把列归0、行+1,反而直接返回
FALSE,导致程序误以为遍历完所有单元格却没找到解 - 递归调用下一个单元格时,传递的行列参数错误,导致递归提前触达终止条件
核心修复:正确的行列遍历逻辑
标准数独回溯遍历要遵循这个流程,你对照自己的代码看看哪里错了:
1. 终止条件要准确
递归函数的第一步必须判断:如果row == 9(因为行索引是0-8),说明所有单元格都处理完毕,直接返回TRUE——这是找到解的标志。
2. 下一个单元格的计算要严谨
从当前(row, col)计算下一个位置的正确逻辑是:
// 伪代码,换成你用的语言 int next_col = col + 1; int next_row = row; if (next_col == 9) { next_col = 0; next_row = row + 1; }
如果你的代码里,列到9时没有归0,直接让row+1,那下一次访问的就是(row+1, 9),直接越界触发Abort Trap。
3. 预设单元格的处理要正确
如果当前单元格是预设数字(不是.),不要尝试填数,直接递归处理下一个单元格,而不是跳过或者返回错误。很多人在这里犯傻,直接跳过不递归,导致遍历中断,提前返回No Solution。
4. 回溯的返回逻辑不能乱
当你尝试一个数字后,递归调用返回TRUE,说明下一层已经找到解了,你要立即返回TRUE,不要继续尝试其他数字;只有当所有1-9都试过都不行,才返回FALSE回溯到上一层。
测试用例的转换要验证
你提到把单行文件转成二维网格,一定要确保转换正确:输入字符串4.....8.5.3..........7......2.....6.....8....刚好是81个字符(9*9),每9个字符对应一行,不要多转或少转,否则网格大小不对也会导致越界。
正确核心逻辑伪代码参考
bool solveSudoku(char grid[9][9], int row, int col) { // 终止条件:所有行处理完成,找到解 if (row == 9) { return true; } // 计算下一个单元格的位置 int next_col = col + 1; int next_row = row; if (next_col == 9) { next_col = 0; next_row = row + 1; } // 当前单元格是预设数字,直接处理下一个 if (grid[row][col] != '.') { return solveSudoku(grid, next_row, next_col); } // 尝试1-9的数字 for (char num = '1'; num <= '9'; num++) { if (isValid(grid, row, col, num)) { grid[row][col] = num; // 递归,如果下一层返回true,说明找到解,直接返回 if (solveSudoku(grid, next_row, next_col)) { return true; } // 回溯,恢复原字符 grid[row][col] = '.'; } } // 所有数字都尝试过,无解,返回false return false; }
你先对照自己的代码,重点查行列递增的边界处理,应该就能解决这俩问题了!
内容的提问来源于stack exchange,提问作者user5402685

