DFS算法
参考:https://www.bilibili.com/video/av12019553?from=search&seid=16531770067247477802
DFS(深度优先搜索)
深度优先搜索算法(英语:Depth-First-Search,简称DFS)是一种用于遍历或搜索树或图的算法。 沿着树的深度遍历树的节点,尽可能深的搜索树的分支。当节点v的所在边都己被探寻过或者在搜寻时结点不满足条件,搜索将回溯到发现节点v的那条边的起始节点。整个进程反复进行直到所有节点都被访问为止。
直到走不下去了再往回走。
主要算法过程:对一个合法的状态A,对其所有的子状态(搜索树的儿子节点),选择一种进行搜索,递归这一过程,直至叶子节点或者目前状态不合法,则回溯至父亲节点,对另一种子状态进行搜索
基本模板
int check(参数)
{
if(满足条件)
return 1;
return 0;
}
void dfs(int step)
{
判断边界
{
相应操作
}
尝试每一种可能
{
满足check条件
标记
继续下一步dfs(step+1)
**恢复初始状态**(回溯的时候要用到)
}
}
入门题型:
-
全排列问题
/** * 字符串的排列 * * 输入一个字符串,按字典序打印出该字符串中字符的所有排列。例如输入字符串abc, * 则打印出由字符a,b,c所能排列出来的所有字符串abc,acb,bac,bca,cab和cba。 * * 输入描述: * 输入一个字符串,长度不超过9(可能有字符重复),字符只包括大小写字母。 * * 思路:DFS解决 * 1,第一步,可以固定第一个元素,对剩下的所有元素进行全排列; * 2,第二部,对于剩下的元素进行全排列,还是固定第一个元素 * DFS * * * @author 梅纸 * */ public class Offer27 { public ArrayList<String> Permutation(String str) { ArrayList<String> list=new ArrayList<>(); if(str==null || str.length()==0) { return list; } char[] str1=str.toCharArray(); prem(str1,0,list); Collections.sort(list); return list; } public void prem(char[] str,int start,ArrayList<String> list) { //终止条件:当start到了最后一个位置 if(start==str.length-1) { //去重 String str2=new String(str); if(list.indexOf(str2)<0) { list.add(str2); } return; } for(int i=start;i<str.length;i++) { //固定首位 swap(str,start,i); //剩下的元素全排列 prem(str,start+1,list); //恢复状态 swap(str,start,i); } } public void swap(char[] str,int i,int j) { char temp=str[i]; str[i]=str[j]; str[j]=temp; } }
题型分类:
写过这些入门题后,我们可以将DFS题分为两大类:
1 . 地图型:这种题型将地图输入,要求完成一定的任务。因为地图的存在。使得题意清楚形象化,容易理清搜索思路。
AOJ 869-迷宫(遍历地图,四向搜索):https://blog.csdn.net/chen_yuazzy/article/details/73656668
HDU 1035-Robot Motion(指定方向搜索,迷路(循环)判断):https://blog.csdn.net/chen_yuazzy/article/details/76285322
HDU 1045-Fire Net(check函数,回溯):https://blog.csdn.net/chen_yuazzy/article/details/76304068
HDU 1010-Tempter of the Bone(奇偶剪枝,回溯):https://blog.csdn.net/chen_yuazzy/article/details/76376960
2 . 数据型:这种题型没有给定地图,一般是一串数字或字母,要求按照一定的任务解题。相对于地图型,这种题型较为抽象,需要在数据中进行搜索。数据以数组的形式存储,那么只要将数组也当作一张图来进行搜索就可以了。
HDU 1016-Prime Ring Problem(回溯、素数筛):https://blog.csdn.net/chen_yuazzy/article/details/76408673
HDU 1258-Sum It Up(双重DFS递归,去重技巧):https://blog.csdn.net/chen_yuazzy/article/details/76408946
HDU 1015-Safecraker(回溯,字符处理):https://blog.csdn.net/chen_yuazzy/article/details/76408846
HDU 2676-Sudoku(抽象,回溯):https://blog.csdn.net/chen_yuazzy/article/details/76242367