zoukankan      html  css  js  c++  java
  • openjudge-最好的草

    http://noi.openjudge.cn/ch0108/17/

    总时间限制: 10000ms   单个测试点时间限制: 1000ms  内存限制: 65536kB
    描述

    奶牛Bessie计划好好享受柔软的春季新草。新草分布在R行C列的牧场里。它想计算一下牧场中的草丛数量。

    在牧场地图中,每个草丛要么是单个“#”,要么是有公共边的相邻两个“#”。给定牧场地图,计算有多少个草丛。

    例如,考虑如下5行6列的牧场地图

    .#....
    ..#...
    ..#..#
    ...##.
    .#....

    这个牧场有5个草丛:一个在第一行,一个在第二列横跨了二、三行,一个在第三行,一个在第四行横跨了四、五列,最后一个在第五行。

    输入
    第一行包含两个整数R和C,中间用单个空格隔开。
    接下来R行,每行C个字符,描述牧场地图。字符只有“#”或“.”两种。
    输出
    输出一个整数,表示草丛数。
    样例输入
    5 6
    .#....
    ..#...
    ..#..#
    ...##.
    .#....
    
    样例输出
    5
    
    来源
    USACO Open 2008 Bronze

    解析:

    广搜。具体步骤就是扫描二维数组,发现'#'号则从该坐标出发进行广搜,搜索的同时把搜过的'#'号修改为'.'   。

     1 #include <stdio.h>
     2 int count=0,R,C;
     3 void bfs(char a[105][105],int i,int j);//从a[i][j]出发做bfs 
     4 int main(int argc, char *argv[])
     5 {
     6     int i,j;
     7     char a[105][105];
     8     //freopen("17.in","r",stdin);
     9     //freopen("17.txt","w",stdout);
    10     scanf("%d%d",&R,&C);
    11     for(i=0;i<R;i++) scanf("%s",a[i]);
    12     
    13     for(i=0;i<R;i++)
    14     {
    15         for(j=0;j<C;j++)
    16         {
    17             if(a[i][j]=='#') bfs(a,i,j);
    18         }
    19     }
    20     printf("%d
    ",count);
    21     return 0;
    22 }
    23 void bfs(char a[105][105],int i,int j)
    24 {
    25     int queueArr[10010][2];
    26     int begin,end,number;//队头,队尾,队列元素数目 
    27     int x,y,xx,yy;
    28     
    29     count++;//草块数目增加1 
    30     
    31     a[i][j]='.';
    32     queueArr[0][0]=i;
    33     queueArr[0][1]=j;
    34     begin=0;
    35     end=1;
    36     number=1;
    37     
    38     while(number>0)//当队列不为空时继续循环
    39     {
    40         //读取队头元素的值 
    41         x=queueArr[begin][0];
    42         y=queueArr[begin][1];
    43         
    44         //查询队头元素的周围节点是否'#' 
    45         xx=x;
    46         yy=y-1;
    47         if(yy>=0&&a[xx][yy]=='#')
    48         {
    49             a[xx][yy]='.';
    50             queueArr[end][0]=xx;
    51             queueArr[end][1]=yy;
    52             end++;
    53             number++;
    54         }
    55         
    56         xx=x;
    57         yy=y+1;
    58         if(yy<C&&a[xx][yy]=='#')
    59         {
    60             a[xx][yy]='.';
    61             queueArr[end][0]=xx;
    62             queueArr[end][1]=yy;
    63             end++;
    64             number++;
    65         }
    66         
    67         xx=x-1;
    68         yy=y;
    69         if(xx>=0&&a[xx][yy]=='#')
    70         {
    71             a[xx][yy]='.';
    72             queueArr[end][0]=xx;
    73             queueArr[end][1]=yy;
    74             end++;
    75             number++;
    76         }
    77         
    78         xx=x+1;
    79         yy=y;
    80         if(xx<R&&a[xx][yy]=='#')
    81         {
    82             a[xx][yy]='.';
    83             queueArr[end][0]=xx;
    84             queueArr[end][1]=yy;
    85             end++;
    86             number++;
    87         }
    88         
    89         begin++;//队头出队 
    90         number--;//队列元素数目减少1个 
    91     }
    92 }

     深搜代码:

     1 #include <stdio.h>
     2 int count=0,R,C;
     3 char a[105][105];
     4 int dx[4]={-1,1,0,0};//上下左右 
     5 int dy[4]={0,0,-1,1};
     6 void dfs(int i,int j);//从a[i][j]出发做bfs 
     7 int main(int argc, char *argv[])
     8 {
     9     int i,j;
    10     
    11     freopen("1.in","r",stdin);
    12     //freopen("1.txt","w",stdout);
    13     scanf("%d%d",&R,&C);
    14     for(i=0;i<R;i++) scanf("%s",a[i]);
    15     
    16     for(i=0;i<R;i++)
    17     {
    18         for(j=0;j<C;j++)
    19         {
    20             if(a[i][j]=='#') { count++; dfs(i,j); }
    21         }
    22     }
    23     printf("%d
    ",count);
    24     return 0;
    25 }
    26 void dfs(int i,int j)//从a[i][j]出发做dfs 
    27 {
    28     int xx,yy;
    29     a[i][j]='.';
    30     for(int k=0;k<4;k++)
    31     {
    32         xx=dx[k]+i;  yy=j+dy[k];
    33         if(xx>=0&&xx<R&&yy>=0&&yy<C&&a[xx][yy]=='#') dfs(xx,yy);
    34     }
    35 }
    View Code

    简化的广搜代码

     1 #include <stdio.h>
     2 int count=0,R,C;
     3 int dx[4]={-1,1,0,0};//上下左右 
     4 int dy[4]={0,0,-1,1};
     5 void bfs(char a[105][105],int i,int j);//从a[i][j]出发做bfs 
     6 int main(int argc, char *argv[])
     7 {
     8     int i,j;
     9     char a[105][105];
    10     freopen("1.in","r",stdin);
    11     //freopen("1.txt","w",stdout);
    12     scanf("%d%d",&R,&C);
    13     for(i=0;i<R;i++) scanf("%s",a[i]);
    14     
    15     for(i=0;i<R;i++)
    16     {
    17         for(j=0;j<C;j++)
    18         {
    19             if(a[i][j]=='#') bfs(a,i,j);
    20         }
    21     }
    22     printf("%d
    ",count);
    23     return 0;
    24 }
    25 void bfs(char a[105][105],int i,int j)
    26 {
    27     int queueArr[10010][2];
    28     int begin,end,number;//队头,队尾,队列元素数目 
    29     int x,y,xx,yy;
    30     
    31     count++;//草块数目增加1 
    32     
    33     a[i][j]='.';
    34     queueArr[0][0]=i;
    35     queueArr[0][1]=j;
    36     begin=0;
    37     end=1;
    38     number=1;
    39     
    40     while(number>0)//当队列不为空时继续循环
    41     {
    42         //读取队头元素的值 
    43         x=queueArr[begin][0];
    44         y=queueArr[begin][1];
    45         //查询队头元素的周围节点是否'#' 
    46         for(int k=0;k<4;k++)
    47         {
    48             xx=dx[k]+x; yy=dy[k]+y;
    49             if(xx>=0&&xx<R&&yy>=0&&yy<C&&a[xx][yy]=='#')
    50             {
    51                 a[xx][yy]='.';
    52                 queueArr[end][0]=xx;
    53                 queueArr[end][1]=yy;
    54                 end++;
    55                 number++;
    56             }
    57         }
    58         begin++;//队头出队 
    59         number--;//队列元素数目减少1个 
    60     }
    61 }
    View Code

    使用STL队列的广搜:

     1 #include<stdio.h>
     2 #include<queue>
     3 using namespace std;
     4 
     5 struct obj
     6 {
     7     int x,y;
     8 };
     9 
    10 int count=0,R,C;
    11 int dx[4]={-1,1,0,0};//上下左右 
    12 int dy[4]={0,0,-1,1};
    13 
    14 void bfs(char a[105][105],int i,int j);//从a[i][j]出发做bfs 
    15 int main(int argc, char *argv[])
    16 {
    17     int i,j;
    18     char a[105][105];
    19     freopen("1.in","r",stdin);
    20     //freopen("1.txt","w",stdout);
    21     scanf("%d%d",&R,&C);
    22     for(i=0;i<R;i++) scanf("%s",a[i]);
    23     
    24     for(i=0;i<R;i++)
    25     {
    26         for(j=0;j<C;j++)
    27         {
    28             if(a[i][j]=='#') bfs(a,i,j);
    29         }
    30     }
    31     printf("%d
    ",count);
    32     return 0;
    33 }
    34 void bfs(char a[105][105],int i,int j)
    35 {
    36     int xx,yy;
    37     queue<struct obj> queA;
    38     struct obj temp;
    39     
    40     count++;//草块数目增加1 
    41 
    42     a[i][j]='.';//访问当前出发点 
    43     temp.x=i;
    44     temp.y=j;
    45     queA.push(temp);//出发点入队 
    46 
    47     while(!queA.empty())//当队列不为空时继续循环
    48     {
    49         //查询队头元素的周围节点是否'#' 
    50         for(int k=0;k<4;k++)
    51         {
    52             xx=dx[k]+queA.front().x;
    53             yy=dy[k]+queA.front().y;
    54             if(xx>=0&&xx<R&&yy>=0&&yy<C&&a[xx][yy]=='#')
    55             {
    56                 a[xx][yy]='.';
    57                 struct obj t;
    58                 t.x=xx;
    59                 t.y=yy;
    60                 queA.push(t);
    61             }
    62         }
    63         queA.pop();//删除队头 
    64     }
    65 }
    View Code

    下面同样是使用了STL队列的广搜,不过在结构体定义时使用了结构体构造函数,可以看看:

     1 #include<stdio.h>
     2 #include<queue>
     3 using namespace std;
     4 
     5 struct obj
     6 {
     7     int x,y;
     8     obj(int xx,int yy){ x=xx;y=yy; }
     9     obj(){ x=0;y=0; }
    10 };
    11 
    12 int count=0,R,C;
    13 int dx[4]={-1,1,0,0};//上下左右 
    14 int dy[4]={0,0,-1,1};
    15 
    16 void bfs(char a[105][105],int i,int j);//从a[i][j]出发做bfs 
    17 int main(int argc, char *argv[])
    18 {
    19     int i,j;
    20     char a[105][105];
    21     freopen("1.in","r",stdin);
    22     //freopen("1.txt","w",stdout);
    23     scanf("%d%d",&R,&C);
    24     for(i=0;i<R;i++) scanf("%s",a[i]);
    25     
    26     for(i=0;i<R;i++)
    27     {
    28         for(j=0;j<C;j++)
    29         {
    30             if(a[i][j]=='#') bfs(a,i,j);
    31         }
    32     }
    33     printf("%d
    ",count);
    34     return 0;
    35 }
    36 void bfs(char a[105][105],int i,int j)
    37 {
    38     int xx,yy;
    39     queue<struct obj> queA;
    40     struct obj temp;
    41     
    42     count++;//草块数目增加1 
    43 
    44     a[i][j]='.';//访问当前出发点 
    45     //temp.x=i;
    46     //temp.y=j;
    47     //queA.push(temp);//出发点入队 
    48     queA.push(obj(i,j));
    49 
    50     while(!queA.empty())//当队列不为空时继续循环
    51     {
    52         //查询队头元素的周围节点是否'#' 
    53         for(int k=0;k<4;k++)
    54         {
    55             xx=dx[k]+queA.front().x;
    56             yy=dy[k]+queA.front().y;
    57             if(xx>=0&&xx<R&&yy>=0&&yy<C&&a[xx][yy]=='#')
    58             {
    59                 a[xx][yy]='.';
    60                 //struct obj t;
    61                 //t.x=xx;
    62                 //t.y=yy;
    63                 //queA.push(t);
    64                 queA.push(obj(xx,yy));
    65             }
    66         }
    67         queA.pop();//删除队头 
    68     }
    69 }
    View Code
  • 相关阅读:
    Linux 系统高级编程 ¶
    手表维修_机械表维修_手表维修网
    epel
    集合包含关系的快速算法 simcity 博客园
    微软的无线鼠标的电池用的快啊,今天又换新的了
    VIM字符集编码设置_icewater_新浪博客
    【索尼LT29i】索尼(SONY)LT29i 3G手机(黑色)WCDMA/GSM 【行情 报价 价格 评测】
    Python模块学习 fileinput 成长的点滴,记录与分享 博客频道 CSDN.NET
    fedora8 使用小记之:终端字体设置
    Wen Quan Yi Open Source Chinese: About
  • 原文地址:https://www.cnblogs.com/huashanqingzhu/p/5663386.html
Copyright © 2011-2022 走看看