F - Oil Deposits

Time Limit:1000MS     Memory Limit:32768KB     64bit IO Format:%I64d & %I64u

Description

GeoSurvComp地质调查公司负责探测地下石油储藏。 GeoSurvComp现在在一块矩形区域探测石油,并把这个大区域分成了很多小块。他们通过专业设备,来分析每个小块中是否蕴藏石油。如果这些蕴藏石油的小方格相邻,那么他们被认为是同一油藏的一部分。在这块矩形区域,可能有很多油藏。你的任务是确定有多少不同的油藏。

Input

输入可能有多个矩形区域(即可能有多组测试)。每个矩形区域的起始行包含m和n,表示行和列的数量,1<=n,m<=100,如果m =0表示输入的结束,接下来是n行,每行m个字符。每个字符对应一个小方格,并且要么是'*',代表没有油,要么是'@',表示有油。

Output

对于每一个矩形区域,输出油藏的数量。两个小方格是相邻的,当且仅当他们水平或者垂直或者对角线相邻(即8个方向)。

Sample Input

 
1 1
*
3 5
*@*@*
**@**
*@*@*
1 8
@@****@*
5 5 
****@
*@@*@
*@**@
@@@*@
@@**@
0 0 
 

Sample Output


0
1
2
2
 
 
解题思路:题目比较短小,容易理解。可以采用广度优先。广度优先采用的典型数据结构是优先队列。这里采用结构体记录位置。
首先从一个@出发,将此位置标记为已访问,并将所有能到达的位置标记为已访问(上下左右及对角线(8个位置),而且存在石油),并且加入队列中,当队列不为空时重复以上操作。为空后,继续枚举未访问而有石油的位置,调用BFS()。由此可见,石油的块数即为调用BFS()的次数。
注意:使用队列时要注意清空(这里while循环中没有其余的跳出循环语句,可以不用清空)。
        每一组数据测试之前对标记数组清零。
        memset()--之前都是一直用memset来清空一维数组
void *memset(void *s, int ch, size_t n);
函数解释:将s中当前位置后面的n个字节 (typedef unsigned int size_t )用 ch 替换并返回 s 。
memset:作用是在一段内存块中填充某个给定的值,它是对较大的结构体数组进行清零操作的一种最快方法.
        二维数组也适用:如memset(vis,0,sizeof(vis));/memset(&vis[0][0],0,sizeof(vis))。第一个参数为要操作数据的首地址。
 
收获感想:对BFS更加理解,之前队列用得也很少,通过做题,知道队列理解也不是那么困难。
 
#include<iostream>
#include<stdio.h>
#include<queue>
#include<cstring>
using namespace std; int vis[][],n,m;
char Map[][]; struct node
{
int x,y;
}; queue<node> q; bool jd(int a,int b)
{
if(a>=&&a<n&&b>=&&b<m&&Map[a][b]=='@')
return true;
else return false;
} void BFS(node n){
while(!q.empty())q.pop();//初始化队列Q;
q.push(n);//可用结构体,也可以哈希一下
while(!q.empty()) {//当q不为空
node temp=q.front();//取出队首元素u;
q.pop();
int cx,cy;
cx=temp.x;
cy=temp.y;
if(jd(cx+,cy)&&vis[cx+][cy]==)
{//此区域合法且有油
vis[cx+][cy]=;//入队;访问标记;
temp.x=cx+;
temp.y=cy;
q.push(temp);
}
if(jd(cx+,cy+)&&vis[cx+][cy+]==)
{
vis[cx+][cy+]=;
temp.x=cx+;
temp.y=cy+;
q.push(temp);
}
if(jd(cx,cy+)&&vis[cx][cy+]==)
{
vis[cx][cy+]=;
temp.x=cx;
temp.y=cy+;
q.push(temp);
}
if(jd(cx-,cy+)&&vis[cx-][cy+]==)
{
vis[cx-][cy+]=;
temp.x=cx-;
temp.y=cy+;
q.push(temp);
}
if(jd(cx-,cy)&&vis[cx-][cy]==)
{
vis[cx-][cy]=;
temp.x=cx-;
temp.y=cy;
q.push(temp);
}
if(jd(cx-,cy-)&&vis[cx-][cy-]==)
{
vis[cx-][cy-]=;
temp.x=cx-;
temp.y=cy-;
q.push(temp);
}
if(jd(cx,cy-)&&vis[cx][cy-]==)
{
vis[cx][cy-]=;
temp.x=cx;
temp.y=cy-;
q.push(temp);
}
if(jd(cx+,cy-)&&vis[cx+][cy-]==)
{
vis[cx+][cy-]=;
temp.x=cx+;
temp.y=cy-;
q.push(temp);
}
}
} int main(){
while(cin>>n>>m)
{
if(n==&&m==) return ; for(int i=;i<n;i++)
for(int j=;j<m;j++)
cin>>Map[i][j]; memset(vis,,sizeof(vis)); int ans=;
node tp;
for(int i=;i<n;i++)
for(int j=;j<m;j++)
{
if(Map[i][j]=='@'&&vis[i][j]==)
{
tp.x=i;tp.y=j;
BFS(tp);
ans++;
}
}
printf("%d\n",ans);
}
return ;
}

CSU-ACM2016暑期集训训练4-BFS(F - Oil Deposits)的更多相关文章

  1. F - Oil Deposits 【地图型BFS+联通性】

    The GeoSurvComp geologic survey company is responsible for detecting underground oil deposits. GeoSu ...

  2. 暑假集训(1)第七弹 -----Oil Deposits(Poj1562)

    Description The GeoSurvComp geologic survey company is responsible for detecting underground oil dep ...

  3. 7.30 正睿暑期集训营 A班训练赛

    目录 2018.7.30 正睿暑期集训营 A班训练赛 T1 A.蔡老板分果子(Hash) T2 B.蔡老板送外卖(并查集 最小生成树) T3 C.蔡老板学数学(DP NTT) 考试代码 T2 T3 2 ...

  4. 2014年CCNU-ACM暑期集训总结

    2014年CCNU-ACM暑期集训总结 那个本期待已久的暑期集训居然就这种.溜走了.让自己有点措手不及.很多其它的是对自己的疑问.自己是否能在ACM这个领域有所成就.带着这个疑问,先对这个暑假做个总结 ...

  5. 2014 SCAU_ACM 暑期集训

    暑期集训,希望能在这段时间获得对得起自己的提升吧 时间:7.11~8.30 集训各专题内容: 1.贪心,递推,基础DP(背包,区间DP,状态压缩DP(去年出了不少于2道铜牌题,看着办)) 2.搜索(B ...

  6. 8.10 正睿暑期集训营 Day7

    目录 2018.8.10 正睿暑期集训营 Day7 总结 A 花园(思路) B 归来(Tarjan 拓扑) C 机场(凸函数 点分治) 考试代码 A B C 2018.8.10 正睿暑期集训营 Day ...

  7. 8.6 正睿暑期集训营 Day3

    目录 2018.8.6 正睿暑期集训营 Day3 A 亵渎(DP) B 绕口令(KMP) C 最远点(LCT) 考试代码 A B C 2018.8.6 正睿暑期集训营 Day3 时间:5h(实际) 期 ...

  8. 8.9 正睿暑期集训营 Day6

    目录 2018.8.9 正睿暑期集训营 Day6 A 萌新拆塔(状压DP) B 奇迹暖暖 C 风花雪月(DP) 考试代码 A B C 2018.8.9 正睿暑期集训营 Day6 时间:2.5h(实际) ...

  9. 8.8 正睿暑期集训营 Day5

    目录 2018.8.8 正睿暑期集训营 Day5 总结 A 友谊巨轮(线段树 动态开点) B 璀璨光滑 C 构解巨树 考试代码 A B C 2018.8.8 正睿暑期集训营 Day5 时间:3.5h( ...

随机推荐

  1. C#-datagridview设置列宽

    在使用datagridview的显示数据的过程中,常常会遇到需要设定datagridview的列宽,这就需要用到datagridview的属性: autosizemode

  2. 使用 Windows 窗体 TextBox 控件创建密码文本框

    密码框是一种 Windows 窗体文本框,它在用户键入字符串时显示占位符. 创建密码文本框 将 TextBox 控件的 PasswordChar 属性设置为某个特定字符. PasswordChar 属 ...

  3. 该优化针对Linux X86_X64环境

    http://netkiller.github.io/www/tomcat/server.html 1. Tomcat优化其实就是对server.xml优化(开户线程池,调整http connecto ...

  4. Nginx详细配置

    #运行用户#user  nobody; #启动进程,通常设置成和cpu的数量相等或者2倍于cpu的个数(具体结合cpu和内存).默认为1worker_processes  1; #全局的错误日志和日志 ...

  5. CSS:表格样式(设置表格边框/文字/背景的样式)

    使用CSS能够制作出十分精美的表格. 代码整理自w3school:http://www.w3school.com.cn 效果图: 代码: <!DOCTYPE html PUBLIC " ...

  6. 信号之alarm和pause函数

    使用alarm函数可以设置一个计时器,在将来某个指定的时间,该计时器会超时.当计时器超时时,产生SIGALRM信号.如果不忽略或不捕捉此信号,则其默认动作是终止调用该alarm函数的进程. #incl ...

  7. PHP之open_ssl

    http://www.wapm.cn/phpdoc/zh/openssl.installation.html http://liuxufei.com/weblog/jishu/376.html dem ...

  8. Moving From Objective-C to C++

    1. virtual method or not: It's better to declare all cpp member methods without "virtual" ...

  9. C# 工厂模式示例

    using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace 工厂模式 ...

  10. Android版本控制系统及其间的差异

    一.何谓版本控制 它是一种软件工程籍以在开发的过程中,确保由不同人所编辑的同一档案都得到更新,它透过文档控制记录程序各个模块的改动,并为每次改动编上序号,并且编辑错误之后还可以回溯到以前的版本 二.可 ...