拓扑排序+代码

拓扑排序

在一个有向无环图中,对所有的节点进行排序,要求没有一个节点指向它前面的节点。

思想:

  1. 先统计所有节点的入度,对于入度为0的节点就可以分离出来,然后把这个节点指向的节点的入度减一。
  2. 一直做改操作,直到所有的节点都被分离出来。
  3. 如果最后不存在入度为0的节点,那就说明有环,不存在拓扑排序,也就是很多题目的无解的情况。

1->3->4->6->2->5(不唯一)

C++代码:

#include <bits/stdc++.h>
#define N 105
using namespace std;

int main()
{
    vector <int> m[N];
    queue <int> q;
    //有些拓扑排序要求字典序最小什么的,那就把队列换成优先队列就好了。
    //priority_queue<int,vector<int>,greater<int> >q;
    vector <int> ans;
    int in[N];
    memset(in,0,sizeof(in));
    int v,e;
    cin>>v>>e;
    for(int i=0;i<e;i++)
    {
        int a,b;
        cin>>a>>b;
        m[a].push_back(b);
    }
    for(int i=1;i<=v;i++)
    {
        for(int j=0;j<m[i].size();j++)
        {
            in[m[i][j]]++;
        }
    }
    for(int i=1;i<=v;i++)
        if(in[i]==0) q.push(i);
    while(!q.empty())
    {
        int p=q.front();q.pop();
        ans.push_back(p);
        for(int i=0;i<m[p].size();i++)
        {
            int y=m[p][i];
            in[y]--;
            if(in[y]==0)
                q.push(y);
        }
    }
    if(ans.size()==v)
    {
        for(int i=0;i<ans.size();i++)
            printf( "%d ",ans[i] );
        printf("
");
    }
    else printf("No Answer!
");
}
原文地址:https://www.cnblogs.com/LMIx/p/10730614.html