您的位置:首页 > 其它

HDU1241 UVa572 Oil Deposits

2016-07-14 08:43 309 查看
问题链接:HDU1241 UVa572 Oil Deposits

本题可以使用深度优先搜索求解。本题用广度优先搜索也可以求解,差别不大。

这个程序说明如下:

1.方向数组 使用方向数组后,各个方向的试探的程序就会变得简洁了,用循环处理即可。

2.避免重复搜索 将搜索过的节点设置为“*”(荒地,非油田),可以避免重复搜索,能够简化程序逻辑。

3.设置边界 通过设置边界,可以免去矩阵(二维数组)的边界判断,简化了程序逻辑。

该问题与图遍历中寻找联通块问题基本上是同构的,算法思路一致。

每当找到一个油田,只需要计数加一,并且使用DFS算法把与其相邻的8个油田擦除即可(避免重复计数)。

想比较网上许多程序而言,这个程序要简洁一些。

AC程序如下:

/* HDU1241 UVa572 Oil Deposits */

#include <stdio.h>
#include <memory.h>

#define DIRECTSIZE 8

struct direct {
int drow;
int dcol;
} direct[DIRECTSIZE] =
{{0, -1}, {0, 1}, {-1, 0}, {1, 0}, {-1, -1}, {-1, 1}, {1, -1}, {1, 1}};

#define MAXN 100

char grid[MAXN+2][MAXN+2];

void dfs(int row, int col)
{
int i;

for(i=0; i<DIRECTSIZE; i++) {
int nextrow = row + direct[i].drow;
int nextcol = col + direct[i].dcol;

if(grid[nextrow][nextcol] == '@') {
grid[nextrow][nextcol] = '*';

dfs(nextrow, nextcol);
}
}
}

int main(void)
{
int m, n, count, i, j;

while(scanf("%d%d", &m, &n) != EOF) {
// 判定结束条件
if(m == 0 && n == 0)
break;

// 清零:边界清零
memset(grid, 0, sizeof(grid));

// 读入数据
for(i=1; i<=m; i++)
scanf("%s", grid[i]+1);

// 计数清零
count = 0;

// 深度优先搜索
for(i=1; i<=m; i++)
for(j=1; j<=n; j++)
if(grid[i][j] == '@') {
count++;
grid[i][j] = '*';
dfs(i, j);
}

// 输出结果
printf("%d\n", count);
}

return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: