zoukankan      html  css  js  c++  java
  • Expm 9_2 有向图的强连通分量问题

     

    【问题描述】

    给定一个有向图,设计一个算法,求解并输出该图的各个强连通分量。

      1 package org.xiu68.exp.exp9;
      2 
      3 import java.util.ArrayList;
      4 import java.util.List;
      5 import java.util.Stack;
      6 
      7 public class Exp9_2 {
      8     public static void main(String[] args) {
      9         int[][] graph=new int[][]{
     10             {0,1,1,0,0},
     11             {1,0,0,0,0},
     12             {0,0,0,1,0},
     13             {0,0,0,0,1},
     14             {0,0,1,0,0}
     15         };
     16         MGraph m1=new MGraph(graph, 5);
     17         m1.getSccs();
     18     }
     19 }
     20 
     21 class MGraph{
     22     private int[][] graph;        //有向图
     23     private int[][] rGraph;        //有向图的反向图
     24     private int vexNum;            //顶点数量
     25     Stack<Integer> stack;        //存储反向图深度优先遍历的post值,从大到小排序
     26     
     27     public MGraph(int[][] graph,int vertexNum){
     28         this.graph=graph;
     29         this.vexNum=vertexNum;
     30         stack=new Stack<>();
     31         rGraph=new int[vexNum][vexNum];    //反向图
     32         
     33         //求原图的反向图
     34         for(int i=0;i<vexNum;i++){
     35             for(int j=i+1;j<vexNum;j++){
     36                 rGraph[i][j]=graph[j][i];
     37                 rGraph[j][i]=graph[i][j];
     38             }
     39         }
     40     }
     41     
     42     
     43     public void getSccs(){
     44         rDFSTraverse();    //先对反向图进行深度优先遍历
     45         
     46         boolean[] visited=new boolean[vexNum];    //记录深度优先遍历原图过程中已经访问的顶点
     47         
     48         List<List<Integer>> sccs=new ArrayList<>();    //存放每一个强连通部件对应的顶点
     49         int n=0;                                    //第几个强连通部件
     50         while(!stack.isEmpty()){
     51             int v=stack.pop();
     52             if(!visited[v]){
     53                 sccs.add(new ArrayList<Integer>());
     54                 DFS(visited,v,sccs,n);
     55                 n++;
     56             }
     57         }
     58         //打印强连通部件
     59         for(int i=0;i<sccs.size();i++){
     60             System.out.print("第"+i+"个强连通部件:");
     61             for(int j=0;j<sccs.get(i).size();j++){
     62                 System.out.print(sccs.get(i).get(j)+" ");
     63             }
     64             System.out.println();
     65         }
     66     }
     67     /*
     68      * 对原图进行深度优先遍历
     69      * 在汇点强连通部件中对某个顶点进行深度优先遍历则刚好访问该强连通部件的所有顶点
     70      */
     71     private void DFS(boolean[] visited,int v,List<List<Integer>> sccs,int n){
     72         sccs.get(n).add(v);
     73         visited[v]=true;
     74         for(int i=0;i<vexNum;i++){
     75             if(graph[v][i]==1 && !visited[i])
     76                 DFS(visited,i,sccs,n);
     77         }
     78     }
     79     
     80 //**************************************************************    
     81     /*
     82      * 对反向图进行深度优先遍历,post值最大的顶点将位于反向图中的一个源点强连通部件,
     83      * 也就是原图中的某个汇点连通部件的某个顶点
     84      * 求得各个顶点的post值,压入栈中
     85      */
     86     public void rDFSTraverse(){
     87         boolean[] visited=new boolean[vexNum];
     88         for(int i=0;i<vexNum;i++){
     89             if(!visited[i]){
     90                 rDFS(visited,stack,i);
     91             }
     92         }
     93     }
     94     //对反向图做深度优先遍历
     95     private void rDFS(boolean[] visited,Stack<Integer> stack,int v){
     96         visited[v]=true;
     97         for(int i=0;i<vexNum;i++){
     98             if(rGraph[v][i]==1 && !visited[i]){
     99                 rDFS(visited,stack,i);
    100             }
    101         }
    102         stack.push(v);
    103     }
    104 }
    View Code
  • 相关阅读:
    方法中的散列可变参数
    方法中的散列可变参数
    策略模式
    策略模式
    HashSet,TreeSet
    HashSet,TreeSet
    ArrayList和LinkedList
    ArrayList和LinkedList
    关于鼠标悬浮标签元素效果(CSS:cursor属性)
    关于鼠标悬浮标签元素效果(CSS:cursor属性)
  • 原文地址:https://www.cnblogs.com/xiu68/p/7988590.html
Copyright © 2011-2022 走看看