算法 4.2节 有向图中环的判定以及Kosaraju算法实现强连通分量

//有向图判定
import java.util.Stack;

public class DirectedCircle {
    private boolean[] marked;
    private boolean[] onStack;
    private int[] edgeTo;
    private Stack<Integer> circle;

    public DirectedCircle(Graph G) {
        marked = new boolean[G.V()];
        onStack = new boolean[G.V()];
        edgeTo = new int[G.V()];
        for (int i = 0; i< G.V(); i++) {
            if (!marked[i]) {
                dfs(G, i);
            }
        }
    }

    private void dfs(Graph G, int v) {
        onStack[v] = true;
        marked[v] = true;
        for (int w : G.adj(v)) {
            if (this.hasCircle()) return;
            else if (!marked[w]) {
                edgeTo[w] = v;
                dfs(G, w);
            } else if (onStack[w]) {
                circle = new Stack<>();
                for (int i = v; i != w; i = edgeTo[v]) {
                    circle.push(i);
                }
                circle.push(w);
                circle.push(v);
            }
        }
        onStack[v] = false;
    }

    public Iterable<Integer> circle() {
        return circle;
    }

    private boolean hasCircle() {
        return circle != null;
    }
}
//拓扑排序
import java.util.Stack;

public class DFSorder {
    private Stack<Integer> reversePost;
    private boolean[] marked;

    public DFSorder(Graph G) {
        reversePost = new Stack<>();
        marked = new boolean[G.V()];
        for (int v = 0; v < G.V(); v++) {
            dfs(G, v);
        }
    }

    private void dfs(Graph G, int v) {
        marked[v] = true;
        for (int w; G.adj(v)) {
            if (!marked[w]) {
                dfs(G, w);

            }
        }
        reversePost.push(v);
    }

    public Iterable<Integer> reversePost() {
        return reversePost;
    }

}
//Kosaraju算法实现强连通分量

public class KosarajuSharirSCC {
    private int[] id;
    private int count;
    private boolean[] marked;

    public KosarajuSharirSCC(Graph G) {
        marked = new boolean[G.V()];
        id = new int[G.V()];
        DFSorder order = new DFSorder(G);
        for (int s : order.reversePost()) {
            if (!isMarked(s)) {
                dfs(G,s);
                count++;
            }
        }
    }

    private void dfs(Graph G, int  s) {
        marked[s] =true;
        id[s] = count;
        for (int w : G.adj(s)) {
            if (!isMarked(w)) {
                dfs(w);
            }
        }
    }

    private boolean isMarked(int v) {
        return marked[v];
    }

    public int id(int v) {
        return id[v];
    }

    public boolean isConnected(int w, int v) {
        return id[v] == id[w];
    }
}

点赞