===================
一、GitHub地址:https://github.com/xiaoknownothing/Fzuwork
二、遇到的困难及解决方法
一看到这个题目感觉可以选定一个空位,扫看所在行,所在列,所在宫,排除数字后选择数字填入,最好的情况所在行列的数字全部填满,这样就简单多了。可是这个数独棋盘只有一个数已知,其他的位子都有9个数要去“猜测”,每行每列每宫格子内数字还不重复,顿时脑子有点大,忙着搜索了一下,看了一些博客,才有了一些大概方向。
三、解题思路
用回溯法求解数独:
- 1.从找第一个空的位子开始,找可选数(排除同行同列同宫重复的数),逐个放入
- 2.找下一个空的位置,找可选数填入,如果这时候,发现此处空白格没有可选数,就回溯,换掉前面的可选数,再继续执行2
- 3.直到空位子都满了就是一个数独解出来了
//找出area[x][y]的可选数
vector <int> find(int x, int y)
{
int a[10] = { 0 };
vector <int> ret;//声明一个int型向量ret
for (int i = 0; i < 9; i++)
{
if (sudu[i][y] > 0)
a[sudu[i][y]] = 1;//所在行若有其他数,标记已使用
if (sudu[x][i] > 0)
a[sudu[x][i]] = 1; //所在列若有其他数,标记已使用
}
int row = x / 3, col = y / 3;//所在宫若有其他数,标记已使用
for (int i = row * 3; i < row * 3 + 3; i++)
{
for (int j = col * 3; j < col * 3 + 3; j++)
{
if (sudu[i][j] > 0)
a[sudu[i][j]] = 1;
}
}
for (int i = 1; i <= 9; i++)
{
if (!a[i]) ret.push_back(i);//逐个填入剩余可选数
}
return ret;
}
void update() {
for (int i = 0; i < 81; i++) area[i].clear();
chosen = make_pair(0, 10);
can_update = false;
for (int i = 0; i < 9; i++ )
{
for (int j = 0; j < 9; j++) if (sudu[i][j]==0)
{
int k = i * 9 + j;//k为该空白格序号
area[k] = find(i, j);//填入可选数
if (area[k].empty()) is_blank = false;//没有可选数
if (area[k].size() < chosen.second) chosen = make_pair(k, area[k].size());//更新
can_update = true;
}
}
}
void num_sudu()
{
update();
if (can_update==false)
{
num++;
if (num >=N) is_over = true;
print();
}
else if (is_blank==false)
{
return;
}
else if (is_over==false)
{
int areaition = chosen.first;
int x = areaition / 9;
int y = areaition - x * 9;//x,y为该位置坐标
int size = chosen.second;//size为选中数个数
vector <int> k = area[areaition];
for (int i = 0; i < size; i++)
{
sudu[x][y] = k[i];
num_sudu();
sudu[x][y] = 0;
is_blank = true;
// 回溯, 还原数据, 原is_blank, 前面的深搜,都没有正确答案,会导致is_blank=false
}
}
}
四、测试
- 运行测试
五、PSP
PSP2.1 | Personal Software Process Stages | 预估耗时(分钟) | 实际耗时(分钟) |
Planning | 计划 | 15 | 40 |
· Estimate | · 估计这个任务需要多少时间 | 15 | |
Development | 开发 | ||
· Analysis | · 需求分析 (包括学习新技术) | 400 | 600 |
· Design Spec | · 生成设计文档 | ||
· Design Review | · 设计复审 (和同事审核设计文档) | ||
· Coding Standard | · 代码规范 (为目前的开发制定合适的规范) | ||
· Design | · 具体设计 | 240 | 260 |
· Coding | · 具体编码 | 180 | 200 |
· Code Review | · 代码复审 | 30 | 40 |
· Test | · 测试(自我测试,修改代码,提交修改) | 60 | 80 |
Reporting | 报告 | 30 | 130 |
· Test Report | · 测试报告 | 30 | |
· Size Measurement | · 计算工作量 | 10 | 10 |
· Postmortem & Process Improvement Plan | · 事后总结, 并提出过程改进计划 | 60 | |
合计 | 640 | 1360 | |