Topological sort using DFS without recursion

后端 未结 7 1529
悲哀的现实
悲哀的现实 2020-12-24 14:37

I know the common way to do a topological sort is using DFS with recursion. But how would you do it using stack instead of recursion? I need to obtai

7条回答
  •  天涯浪人
    2020-12-24 15:11

    Here we go again. :-) I am submitting an answer, because I do not have enough points to make comments. :-(

    Well let me say that I like this algorithm a lot. If the graph is defined in the right way, then there is no error. But take this graph:

    vector> graph
    {
         { 2, 1 }
        ,{ 2 }
        ,{ }
    };
    

    This will display: 2 1 2 0

    To protect yourself from graphs defined in that way or where the edges that come in are random you can do this:

    #include 
    #include 
    #include 
    #include 
    using namespace std;
    
    int main()
    {
        stack> dfs;
        stack postorder;
        vector newvector;
        vector::iterator it;
        vector> graph
        {
             { 2, 1 }
            ,{ 2 }
            ,{ }
        };
    
        vector visited(graph.size());
        vector finallyvisited(graph.size());
    
        for (int i = 0;i < graph.size();i++)
        {
            if (!visited[i])
            {
                dfs.push(make_pair(false, i));
            }
    
            while (!dfs.empty())
            {
                pair node = dfs.top();
                dfs.pop();
                if (node.first)
                {
                    if (!finallyvisited[node.second])
                    {
                        finallyvisited[node.second] = true;
                        postorder.push(node.second);
                        cout << node.second << endl;
                    }
                    continue;
                }
    
                visited[node.second] = true;
                dfs.push(make_pair(true, node.second));
                newvector = graph[node.second];
                for (it = newvector.begin();it != newvector.end();it++)
                {
                    int son = *it;
                    if (!visited[son])
                    {
                        dfs.push(make_pair(false, son));
                    }
                }
            }
        }
        return 0;
    }
    

    Or you could preorder the graph, maybe someone could show that solution. How to preorder randomly given edges that there is no need for second check. :-)

    And I did though over the Atif Hussain comment and it is erroneous. That would never work. You always want to push down the stack a node as late as possible so it pops as first as possible.

提交回复
热议问题