【软件工程基础】个人项目报告之生成数独题目

本文档详细介绍了使用C++实现数独题目生成的过程,包括项目背景、需求分析、概要设计和代码实现。在需求分析中,强调了在数独终局基础上随机挖空的规则。概要设计部分描述了随机选择挖空位置的策略,并确保每个宫至少有两个空格。代码实现部分涵盖了读取数独终局、生成挖空位置等关键步骤,最终实现生成30-60个空格的数独题目。
项目地址

[github]链接: https://github.com/kindoms214/Sudoku.
 
项目专栏地址: https://blog.csdn.net/kindoms214/category_9638585.html.
1、个人项目报告之可行性分析、需求分析、概要设计: https://blog.csdn.net/kindoms214/article/details/103909657.
2、个人项目报告之生成数独终局: https://blog.csdn.net/kindoms214/article/details/103964265.
3、个人项目报告之生成终局代码优化: https://blog.csdn.net/kindoms214/article/details/104001320.
4、个人项目报告之求解数独: https://blog.csdn.net/kindoms214/article/details/103997960.
5、个人项目报告之求解代码优化: https://blog.csdn.net/kindoms214/article/details/104036705.
6、个人项目报告之生成数独题目: https://blog.csdn.net/kindoms214/article/details/104017290.
7、个人项目报告之单元测试及分支覆盖率: https://blog.csdn.net/kindoms214/article/details/104041445.
 

  从整个个人项目来看,生成数独题目的部分似乎是附加题中的要求,但是想要分析求解数独的算法工作效率、解决求解数独算法上的瓶颈,设计实现生成数独终局的算法是非常有必要的。
 

需求分析

  因为这一部分的设计并不算是包括在个人项目必做部分中的,所以在一开始的需求分析中并没有涉及到这一部分的需求分析,所以在具体实现这一部分算法的时候,有必要进行完整的软件生命周期法的分析。
  在项目中,要求数独题目的生成是在数独终局的基础之上进行挖空。但挖空并不是乱挖,虽然也是随机的进行挖空,但是还是有一定的前提要求。首先,每一宫中至少要挖去两个空,除此之外,还要求总的挖空数在30-60个之间。
 

概要设计

  既然是随机挖空,肯定是使用随机数进行空的选择。然后对于项目的两个要求,我选择先满足每一宫中挖两个,再满足总数在30-60之间的要求。
 

代码实现

  最开始是读入数独终局,这一步的方法和求解数独的第一步一样,只不过求解数独读的是题目,生成数独题目读的是数独终局,这里就不再进行描述了。
  在每一宫中,对于生成要挖的空的位置,必须得保证产生的两个随机数不一样,毕竟一样的话可能导致需求无法满足。除此之外,还要避免左上角的固定数字被挖掉。下面是详细的代码:

//先在每个宫取出两个
	for (int k = 0; k < 9; k++)
	{
		int i, j, hole[2];//3*3里面掏的位置
		hole[0] = rand() % 9;
		hole[1] = rand() % 9;

		//随机生成两个空
		while (k == 0 && hole[0] == 0)	//防止左上角的数被删掉
		{
			hole[0] = rand() % 9;
		}
		while (k == 0 && hole[1] == 0)	//防止左上角的数被删掉
		{
			hole[1] = rand() % 9;
		}
		while (hole[0] == hole[1])//防止重复
		{
			hole[1] = rand() % 9;
		}

		delete_sudoku[3 * (k / 3) + hole[0] / 3][3 * (k % 3) + hole[0] % 3] = 0;
		delete_sudoku[3 * (k / 3) + hole[1] / 3][3 * (k % 3) + hole[1] % 3] = 0;
	}

  下面就得满足第二个条件:总挖空数在30-60。因为每一宫中已经挖掉两个空了,所以还需要挖的空的数量在12-42之间,

//还需要取出12-42个
	int additional;
	additional = 12 + rand() % 31;	//决定要取的个数

	while (additional--)
	{
		int k = rand() % 81;
		int i = k / 9;
		int j = k % 9;

		if (delete_sudoku[i][j] != 0 && (i+j)!= 0)
			delete_sudoku[i][j] = 0;
		else additional++;
	}

  到此为止,生成数独题目的需求就已经实现了,至于代码性能方面,因为读入数独终局使用的求解数独部分的读入数独题目的方法,所以就没必要再进行性能方面的优化了,因为再想要优化的话,就只能修改挖空的算法了。因为在需求分析中就已经明确了更换算法的不必要性,所以整个对数独题目生成需求的开发工作就已经完成。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值