[LintCode] Find the Weak Connected Component in the Directed Graph

 

Find the number Weak Connected Component in the directed graph. Each node in the graph contains a label and a list of its neighbors. (a connected set of a directed graph is a subgraph in which any two vertices are connected by direct edge path.)html

Example

Given graph:node

A----->B  C
 \     |  | 
  \    |  |
   \   |  |
    \  v  v
     ->D  E <- F

Return {A,B,D}, {C,E,F}. Since there are two connected component which are{A,B,D} and {C,E,F}this

Note

Sort the element in the set in increasing order.spa

Solution:code

并查集。遍历每一条变,更新每一个节点所在集合。component

/**
 * Definition for Directed graph.
 * struct DirectedGraphNode {
 *     int label;
 *     vector<DirectedGraphNode *> neighbors;
 *     DirectedGraphNode(int x) : label(x) {};
 * };
 */
class Solution {
    //use union-set to solve
private:
    int find(unordered_map<int, int> &nodeMap, int label){
        if(nodeMap.find(label) == nodeMap.end()){
            nodeMap[label] = label;
            return label;
            //if this node doesn't belong to any union-set, create a new set
        }else{
            //this node belongs to some set, find the root of the set
            int res = nodeMap[label];
            while(nodeMap[res] != res)
                res = nodeMap[res];
            return res;
        }
    }
public:
    /**
     * @param nodes a array of directed graph node
     * @return a connected set of a directed graph
     */
    vector<vector<int>> connectedSet2(vector<DirectedGraphNode*>& nodes) {
        unordered_map<int, int> nodeMap;
        vector<vector<int> > result;
        for(int i = 0;i < nodes.size();++i){
            for(int j = 0;j < (nodes[i]->neighbors).size();++j){
                int s1 = find(nodeMap, nodes[i]->label);
                int s2 = find(nodeMap, (nodes[i]->neighbors)[j]->label);
                if(s1 != s2){
                    //union two sets
                    if(s1 < s2) nodeMap[s2] = s1;
                    else nodeMap[s1] = s2;
                }else{
                    //do nothing
                }
            }
        }
        
        unordered_map<int, int> setId2VecId;
        for(int i = 0;i < nodes.size();++i){
            int label = nodes[i]->label;
            int setId = find(nodeMap, label);
            if(setId2VecId.find(setId) == setId2VecId.end()){
                vector<int> vec;
                setId2VecId[setId] = result.size();
                result.push_back(vec);
            }
            int idx = setId2VecId[setId];
            result[idx].push_back(label);
        }
        for(int i = 0;i < result.size();++i)
            sort(result[i].begin(), result[i].end());
        
        return result;
    }
};

Inspired by: http://www.cnblogs.com/easonliu/p/4607300.htmlhtm