软件工程基础——个人项目

一、项目地址

代码托管在了GitHub上,附上链接如下:

GitHub链接

二、PSP

PSP2.1Personal Software Process Stages预计耗时(min)实际耗时(min)
Planing计划
·Estimate·估计这个任务需要多少时间
Development开发
·Analysis·需求分析(包括学习新技术)120
·Design Spec·生成设计文档60
·Design Review设计复审(和同事审核设计文档)30
·Coding Standard·代码规范(为目前的开发制定合适的规范)60
·Design·具体设计120
·Coding·具体编码1080
·Coding Review·代码复审60
·Test测试(自我测试,修改代码,提交测试)300
Reporting报告60
·Test Report·测试报告60
·Size Measurement·计算工作量60
·Postmortem & Process Improvement Plan·时候总结,并提出过程改进计划60
合计

三、需求分析

生成终局

输入参数:sudoku.exe -c 20(生成数独终局的数目)	
a. 生成指定数量的数独终局
b. 能处理非法参数
c. 左上角第一个数固定(9+7)%9+1=8
d. 输入范围限制在1~1000,要求在60s内给出结果
e. 结果输出到文件sudoku.txt中并要求可被覆盖

求解数独

输入参数sudoku.exe -s absolute_path_puzzlefile
a. 从指定文件中读取数据,并将结果输出到指定文件中
b. 保证文件中数独格式正确
c. 结果的格式要与生成终局的格式相同

四、解题思路描述

项目包括生成指定个数的数独终局以及求解给定的数独终局,因此要弄懂数独生成算法以及求解数独的算法。首先想到的解决办法就是回溯法,对单个数字进行填充,如果的得到的结果不满足条件的话,我们就回溯到上一层,知道求出正解。在搜索引擎输入求解数独可以得知Dancing Links算法是求解数独常用的算法,算法原理比较容易理解,它实际上是一种数据结构(交叉十字循环双向链)。由于解决精确覆盖问题的X算法中需要频繁用到移除、恢复操作,而在这种结构下,进行这两种操作的效率极高。

跳跃的舞者,舞蹈链算法(Dancing Links)------求解精确覆盖问题

五、设计实现过程

首先分析出程序流程如下:

Created with Raphaël 2.2.0 开始 输入指令 分析指令 求解数独 输出数据 结束 生成终局 yes no

列出需要的函数如下:

extern int Read(char str[]); //读取参数并判断参数是否合法
extern int Random_Init(int Num[]); //随机初始化第一行
extern int Judge_Sudoku(int s, int x, int y, int num); //判断数独终局知否合法
extern int Fill_Sudoku(int s, int x, int y); //填充数独
extern int Creat_Sudoku(int Sodoku_Num); //创建数独终局
extern int Solve_Sudoku(char File[]); //解数独残局

五、性能改进

对于第一个可执行的版本,对其进行性能测评,结果如下图所示:

性能分析报告
具体函数模块

可见函数输出占据了大量时间,于是我将输出改为putchar之后,大量减少了输出时间。

六、代码说明

Fill_Sudoku这一部分函数在很多地方都有调用,将此部分代码拎出来作为重点。

int Fill_Sudoku(int s, int x, int y)				//填充函数
{    
	int Trace_back = Board[s][x][y];
	int next_x = x + (y + 1) / 9;					//定义下一方格横坐标
	int	next_y = (y + 1) % 9;						//定义下一方格坐标
	
	if (x > 8)
		return 1;
		
	if (Board[s][x][y]) 
	{
		if (Fill_Sudoku(s, next_x, next_y))
			return 1;
	}
	else 
	{	
		int i;
		for (i = 0; i < 9; i++)						//判断合法性
		{
			int Try_Num = Try_List[i];
			if (Judge_Sudoku(s, x, y, Try_Num))
			{
				Board[s][x][y] = Try_Num;
				if (Fill_Sudoku(s, next_x, next_y))
					return 1;
			}
		}
	}

	Board[s][x][y] = Trace_back;
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值