深度搜索

深度搜索又叫深度优先遍历(DFS,Depth-firstSearch),是搜索常用的手段之一。它从一个状态出发,不断地转移状态,直到无法转移,就回退到前一步的状态,继续转移到其他状态,这样不断地重复下去,直到找到最终的解为止。下面就以poj和woj上的两个经典题目为例进行简单地说明。

poj2386  Lake Counting

题目链接:

http://poj.org/problem?id=2386

题目的大概意思就是有一个N*M的园子,雨后积水。八连通的积水被认为是连接在一起的。指定输出,给出水洼的数目。数据规模:1 <= N <= 100; 1 <= M <= 100,时间限制是1s,内存限制是65536KB。

这就是一道很经典的深度搜索问题,一些公司的笔试也经常出这种题目。可以这样考虑,从任意的w地方开始出发,每次遇到四周的邻接w就替换成“·”。一次进行DFS后,与初始的这个w开始邻接的所有的w就被替换成了“·”,直到图中不再存在w为止,总共进行的DFS的次数就是要输出的答案。时间复杂度为O(8*N*M)=O(N*M)。

AC代码如下:

#include<iostream>
#include<stdio.h>
using namespace std;
const int MAX_N=101;
const int MAX_M=101;
int n,m;
char field[MAX_N][MAX_M];
void dfs(int x,int y)
{
	field[x][y]='.';
	for(int dx=-1;dx<=1;++dx)
	{
		for(int dy=-1;dy<=1;++dy)
		{
			int nextX=x+dx,nextY=y+dy;
			if(nextX>=0&&nextX<n&&nextY>=0&&nextY<m&&field[nextX][nextY]=='W')
				dfs(nextX,nextY);
		}
	}
	return ;
}
int main()
{
	freopen("in.txt","r",stdin);
	while(cin>>n>>m)
	{
		for(int i=0;i<n;++i)
		{
			for(int j=0;j<m;++j)
			{
				cin>>field[i][j];
			}
		}
		int ans=0;
		for(int i=0;i<n;++i)
		{
			for(int j=0;j<m;++j)
			{
				if(field[i][j]=='W')
				{
					dfs(i,j);
					ans++;
				}
			}
		}
		cout<<ans<<endl;
	}
	return 0;
}

woj1167 Oil Detecting

题目链接:

http://acm.whu.edu.cn/learn/problem/detail?problem_id=1167

跟上一题几乎一样,解法也一样。AC代码如下:

/*
Name:Li Jiansong
Copyright:
Author:
Date: 04/01/16 03:34
Description: woj1167
深度搜索
*/
#include<iostream>
#include<stdio.h>
using namespace std;
#pragma warning(disable:4996)
int r, c;
int dx[] = { 0, 1, -1, 1, -1, 0, 1, -1 };
int dy[] = { 1, 1, 1, 0, 0, -1, -1, -1 };
int nextX, nextY;
char matrix[100][100];
void Dfs(int x, int y)
{
	if (x<c&&x >= 0 && y<r&&y >= 0)
	{
		if (matrix[y][x] == 'O')
		{
			matrix[y][x] = 'X';
			for (int i = 0; i<8; i++)
			{
				nextX = x + dx[i];
				nextY = y + dy[i];
				Dfs(nextX, nextY);
			}
		}
		else return;
	}
	else return;
}

int main()
{
	freopen("in.txt", "r", stdin);
	freopen("out.txt", "w", stdout);
	int count;
	while (cin >> r >> c&&r != 0 && c != 0)
	{
		count = 0;
		for (int i = 0; i<r; ++i)
		{
			for (int j = 0; j<c; ++j)
			{
				cin >> matrix[i][j];
			}
		}
		for (int i = 0; i<r; ++i)
		{
			for (int j = 0; j<c; ++j)
			{
				if (matrix[i][j] == 'O')
				{
					count++;
					Dfs(j,i);
				}
			}
		}
		cout << count << endl;
	}
	return 0;
}

你可能感兴趣的:(DFS)