今天刚接触深度优先的算法,核心是聚焦在当下怎么做,至于下一步怎么则可调用当下怎么做的代码实现,就是递归思想。我下面依托一个具体例子来解释它。
我认为它的应用方面更多的是暴力枚举的代替。比如我刚刚看过的一个例子:A+B=C。A,B,C都是三位数,A、B、C每一位的可能数字是1-9,并且每一位的数字各不相同,让把所有可能的情况找出来。
那么很多人会想到定义九个变量,然后九重循环,范围都是1-9,满足A+B=C并且满足各不相同就输出。这就是枚举的方法。
不过还有一种方法就是深度优先搜索,填的时候就是按照1-9的顺序去填的。可以想到有九个位置,如果我要把第一个位置的数填好,那么我们可以使用第一个位置的数的填法 去填第二个数。第三个数。。。直到第九个数填好后再填第十个位置的数时候改为输出这组结果就行了。
代码如下
void dfs(int step)//这就是填具体一个位置时候调用的函数,接收的参数step表示对当前第step个位置填数字
{
int i;
if (step == 10)//当九个位置填好,再调用dfs()函数进入
{
if(a[1]*100+a[2]*10+a[3]+a[4]*100+a[5]*10+a[6]==a[7]*100+a[8]*10+a[9])//数组a从a[1]到a[9]代表九个位置,里面的值代表九个位置的数
printf("%d%d%d+%d%d%d=%d%d%d\n", a[1], a[2], a[3], a[4], a[5], a[6], a[7], a[8], a[9]);
return;//这个return表示一种情况的结束,必须写
}
for (i = 1; i <= 9; i++)//对于具体的一个位置,我们都是从1-9试验
{
if (book[i] == 0)//表示如果之前没有被使用,此处的book[1]-book[9]记录1-9的数是否被用过,等于0表示没用过,等于1表示用过
{
a[step] = i;//就填入这个数
book[i] = 1;//标记已用
dfs(step + 1);//step位置填完后,再调用dfs函数,填step+1的位置数
book[i] = 0;//此处赋值为零可以理解为 在输出一种情况后,取出现在位置上的数重新填。
}
}
}
需要注意的是int a[10],book[10]是全局变量,因为不断地调用dfs函数,每一次调用都要用到a与book的数据,必须一直存在才行。
这是部分运行效果,可以看到深度优先算法还是能解决这样的问题的