zoukankan      html  css  js  c++  java
  • 全球变暖 蓝桥杯

    标题:全球变暖
    
    你有一张某海域NxN像素的照片,"."表示海洋、"#"表示陆地,如下所示:
    
    .......
    .##....
    .##....
    ....##.
    ..####.
    ...###.
    .......
    
    其中"上下左右"四个方向上连在一起的一片陆地组成一座岛屿。例如上图就有2座岛屿。  
    
    由于全球变暖导致了海面上升,科学家预测未来几十年,岛屿边缘一个像素的范围会被海水淹没。具体来说如果一块陆地像素与海洋相邻(上下左右四个相邻像素中有海洋),它就会被淹没。  
    
    例如上图中的海域未来会变成如下样子:
    
    .......
    .......
    .......
    .......
    ....#..
    .......
    .......
    
    请你计算:依照科学家的预测,照片中有多少岛屿会被完全淹没。  
    
    【输入格式】
    第一行包含一个整数N。  (1 <= N <= 1000)  
    以下N行N列代表一张海域照片。  
    
    照片保证第1行、第1列、第N行、第N列的像素都是海洋。  
    
    【输出格式】
    一个整数表示答案。
    
    【输入样例】
    7
    .......
    .##....
    .##....
    ....##.
    ..####.
    ...###.
    .......
    
    【输出样例】
    1  
    
    
    
    资源约定:
    峰值内存消耗(含虚拟机) < 256M
    CPU消耗  < 1000ms
    
    
    请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。
    
    所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
    不要使用package语句。不要使用jdk1.7及以上版本的特性。
    主类的名字必须是:Main,否则按无效代码处理。

    解题思路:

    先清楚求的是有多少个岛屿会被淹没,而不是最后剩下几个岛屿。

    其实问题很简单,只要知道一开始有多少个岛屿,淹没后剩下几个岛屿,相减即是答案。

    淹没陆地的操作很简单,扫描陆地,只要满足上下左右四个方向有一个方向上是海,那这片陆地就赋值为海,所以淹没后海域的情况就求出来了。

    所以知道一个海域上有几个岛屿是关键,只要解决了这个问题就成功解题了。

    求海域上有几个岛屿很DFS即可,扫描整片海域,扫描到一个没有扫描过的陆地像素点,它一定属于某个岛屿,所以岛屿数量+1,

    然后以此像素点为起点进行深度(广度)优先搜索,搜索到的每一个陆地像素点都属于此片陆地,所以将其标记为已扫描,扫描结束后继续向下扫描此片海域,扫描到下一个没有已扫描的陆地,岛屿数量再次+1,继续重复上述的操作。

    import java.io.IOException;
    import java.util.Scanner;
    
    public class Main {
        
        static int old=0;
        static int now=0;
        static int N;
        static char array[][];
        static char arrayB[][];
        static int x[]={-1,0,1,0};    //上左下右
        static int y[]={0,1,0,-1};
        
        static void solve(char array[][],int i,int j){
            array[i][j]='.';
            for(int d=0;d<4;d++){
                int dx=i+x[d];
                int dy=j+y[d];
                if(dx<0 || dy<0 || dx>N-1 || dy>N-1){    //越界判断
                    continue;
                }
                if(array[dx][dy]=='#'){    //深搜覆盖这个岛屿
                    array[dx][dy]='.';
                    solve(array,dx,dy);
                }
            }
        }
    
        public static void main(String[] args) throws IOException {
            Scanner reader=new Scanner(System.in);
            N=reader.nextInt();
            array=new char[N][N];
            arrayB=new char[N][N];
            for(int i=0;i<N;i++){
                String s=reader.next();
                array[i]=s.toCharArray();
                arrayB[i]=s.toCharArray();
            }
            //第一次扫描
            for(int i=0;i<N;i++){
                for(int j=0;j<N;j++){
                    if(array[i][j]=='#'){
                        old++;
                        solve(array,i,j);
                    }
                }
            }
            //淹没陆地
            for(int i=0;i<N;i++){
                for(int j=0;j<N;j++){
                    if(arrayB[i][j]=='#'){
                        if(i-1>=0){
                            if(arrayB[i-1][j]=='.'){
                                arrayB[i][j]='*';
                            }
                        }
                        if(j+1<=N-1){
                            if(arrayB[i][j+1]=='.'){
                                arrayB[i][j]='*';
                            }
                        }
                        if(i+1<=N-1){
                            if(arrayB[i+1][j]=='.'){
                                arrayB[i][j]='*';
                            }
                        }
                        if(j-1>=0){
                            if(arrayB[i][j-1]=='.'){
                                arrayB[i][j]='*';
                            }    
                        }
                    }
                }
            }
            //第二次扫描
            for(int i=0;i<N;i++){
                for(int j=0;j<N;j++){
                    if(arrayB[i][j]=='#'){
                        now++;
                        solve(arrayB,i,j);
                    }
                }
            }
            System.out.println(old-now);
        }
    }
  • 相关阅读:
    53. Maximum Subarray
    64. Minimum Path Sum
    28. Implement strStr()
    26. Remove Duplicates from Sorted Array
    21. Merge Two Sorted Lists
    14. Longest Common Prefix
    7. Reverse Integer
    412. Fizz Buzz
    linux_修改域名(centos)
    linux_redis常用数据类型操作
  • 原文地址:https://www.cnblogs.com/chiweiming/p/10467293.html
Copyright © 2011-2022 走看看