力扣200岛屿数量解法3种

DFS BFS 并查集 三种方式解决岛屿问题

java 复制代码
import java.util.*;
public class Edit {
    //并查集版本
    public int numIslandsUnion(char[][] grid) {
        UnionSet unionfind = new UnionSet(grid);
        //unionfind.UnionSet(grid);
        for(int clow=1;clow<unionfind.clow;clow++){
            if(grid[0][clow-1]=='1'&&grid[0][clow]=='1'){
                unionfind.union(0,clow,0,clow-1);
            }
        }
        for(int row=1;row<unionfind.row;row++){
            if(grid[row-1][0]=='1'&&grid[row][0]=='1'){
                unionfind.union(row,0,row-1,0);
            }
        }
        for(int row=1;row<unionfind.row;row++){
            for(int clow=1;clow<unionfind.clow;clow++){
                if(grid[row][clow-1]=='1'&&grid[row][clow]=='1'){
                    unionfind.union(row,clow,row,clow-1);
                }
                if(grid[row-1][clow]=='1'&&grid[row][clow]=='1'){
                    unionfind.union(row,clow,row-1,clow);
                }
            }
        }
        return unionfind.sets;
    }



    //bfs版本
    public int numIslandsBfs(char[][] grid) {
        Queue<int[]> que = new LinkedList<int[]>();
        int count=0;
        for(int i=0;i<grid.length;i++){
            for(int j=0;j<grid[0].length;j++){
                if(grid[i][j]=='1'){
                    que.add(new int[]{i,j});
                    while(!que.isEmpty()){
                        int[] cur = que.poll();
                        int tempi= cur[0];
                        int tempj= cur[1];
                        if(tempi>=0&&tempj>=0&&tempj<grid[0].length&&tempi<grid.length&&grid[tempi][tempj]=='1'){
                            grid[tempi][tempj]='0';
                            que.add(new int[]{tempi+1,tempj});
                            que.add(new int[]{tempi-1,tempj});
                            que.add(new int[]{tempi,tempj+1});
                            que.add(new int[]{tempi,tempj-1});
                        }
                    }
                    count++;
                }

            }
        }
        return count;
    }

    //dfs版本
    public int numIslandsdfs(char[][] grid) {
        int count=0;
        for(int i=0;i<grid.length;i++){
            for(int j=0;j<grid[0].length;j++){
                if(grid[i][j]=='1'){
                    dfs(grid,i,j);
                    count++;
                }

            }
        }
        return count;
    }
    public void dfs(char[][] grid,int i,int j){
        if(i<0||j>=grid[0].length||i>=grid.length||j<0||grid[i][j]=='0'||grid[i][j]=='2'){
            return;
        }
        grid[i][j]='2';
        dfs(grid,i+1,j);
        dfs(grid,i-1,j);
        dfs(grid,i,j+1);
        dfs(grid,i,j-1);
        return;
    }
    //并查集方法
    public static class UnionSet{
        private int[] parents;//存父节点
        private int[] size;//存的大小
        private int[] help;//辅助数组,当作栈
        private int  clow;
        private int  row;
        private int  sets;

        //先初始化,values传入进来的数组
        public  UnionSet(char[][] values){
            sets=0;
            row = values.length;
            clow = values[0].length;
            int length = clow*row;
            parents = new int[length];//每个元素的负类
            size = new int[length];
            help = new int[length];
            for(int i=0;i<row;i++){
                for(int j=0;j<clow;j++){
                    int in =index(i,j);
                    if(values[i][j]=='1'){
                        parents[in]=in;
                        size[in]=1;
                        sets++;
                    }
                }
            }

        }
        public  int index(int x,int y){
            return x*clow+y;
        }
        //找寻当前节点的最上面的节点
        public int findHead(int cur){
            int index=0;
            //路径压缩,利用help数组存储,从当前节点cur访问到顶部节点所经过的节点
            //最后将所储存的节点的父节点全部设置为顶部节点,利用顶部节点来代表这个集合
            while(cur!=parents[cur]){
                help[index++]=cur;
                cur=parents[cur];
            }
            for (index--;index==0;index--){
                parents[help[index]]=cur;
            }
            return cur;
        }
        //判断是否是同一个集合
        public boolean isSameSet(int a,int b){
            //从a和b分别开始找顶部节点,若节点相同则认为在同一个集合,若不同则不在同一个集合
            return findHead(a)==findHead(b)?true:false;
        }
        //将a和b放入到一个集合当中
        public void union(int row1,int clow1 ,int row2,int clow2){
            int a = index(row1,clow1);
            int b = index(row2,clow2);
            int aHead=findHead(a);
            int bHead=findHead(b);
            if(aHead!=bHead){
                //将规模较小的集合插入大集合当中
                int asize = size[aHead];
                int bsize= size[bHead];
                int big= asize>=bsize?aHead:bHead;
                int small= asize<bsize?aHead:bHead;
                parents[small]=big;
                size[big]=asize+bsize;
                size[small]=0;
                sets--;
            }
        }

    }
    
}
相关推荐
吃什么芹菜卷1 分钟前
深度学习:词嵌入embedding和Word2Vec
人工智能·算法·机器学习
wclass-zhengge5 分钟前
数据结构与算法篇(树 - 常见术语)
数据结构·算法
labuladuo52011 分钟前
AtCoder Beginner Contest 372 F题(dp)
c++·算法·动态规划
夜雨翦春韭12 分钟前
【代码随想录Day31】贪心算法Part05
java·数据结构·算法·leetcode·贪心算法
hsling松子5 小时前
使用PaddleHub智能生成,献上浓情国庆福
人工智能·算法·机器学习·语言模型·paddlepaddle
dengqingrui1236 小时前
【树形DP】AT_dp_p Independent Set 题解
c++·学习·算法·深度优先·图论·dp
C++忠实粉丝6 小时前
前缀和(8)_矩阵区域和
数据结构·c++·线性代数·算法·矩阵
ZZZ_O^O6 小时前
二分查找算法——寻找旋转排序数组中的最小值&点名
数据结构·c++·学习·算法·二叉树
CV-King7 小时前
opencv实战项目(三十):使用傅里叶变换进行图像边缘检测
人工智能·opencv·算法·计算机视觉
代码雕刻家7 小时前
数据结构-3.9.栈在递归中的应用
c语言·数据结构·算法