拓扑排序

来源:互联网 发布:单片机创新大赛 编辑:程序博客网 时间:2024/05/29 07:55

拓扑排序

定义:对有向无环图(DAG)进行拓扑排序,是将G中所有顶点排成一个线性序列,并且有先后关系次序,使得任意一对顶点u和v,即<u,v>,u都出现在v之前。

实现方法

1.从DAG中寻找入度为0的顶点,并将它输入,作为已经排序出来的顶点.

2.从图中删除第一步中的顶点,并与之相邻的边都做相应的调整,即入度减1(若存在相邻关系).

3.重复第一和第二步,直至所有顶点均输出.

 

拓扑排序代码:

#include<iostream>#include<stack>using namespace std;struct DAG         //有向无环图中的边 {    char w1,w2;int  weight;};#define M 100int e;                  //M最大顶点数,e边数 char data[M];          //n个顶点代表每个顶点的字符int Edge[M][M];       //顶点对应的权值,若存在,则假设不权值为0int Degree[M];        //存储每个节点的入度int visited[M];//初始化图 void InitGraph(int t)       {int i,j;for(i=0;i<t;++i){ data[i]='a'+i; visited[i]=0; for(j=0;j<t;++j) Edge[i][j]=0;}}void MakeGraph(DAG d[],int len){int j,i=0;while(i<len){Edge[d[i].w1-'a'][d[i].w2-'a']=d[i].weight;++i;}}void TopSort(int t){stack<int> s;//统计结点的入度 int i,j,count=0,d,result;for(j=0;j<t;++j){d=0;for(i=0;i<t;++i){ if(Edge[i][j]!=0) d++;} Degree[j]=d;    //j的入度为d if(Degree[j]==0) s.push(j);}while(count<t)         //count为已经排序出来的顶点个数{  if(!s.size()) break;       //栈中已没有入度为0的顶点  result=s.top();   s.pop();              //压出入度为0的顶点  count++;   visited[result]=1;     //标记该节点已被访问过   cout<<data[result]<<" ";      for(i=0;i<t;++i)  {if(Edge[result][i]!=0) { Degree[i]--;Edge[result][i]=0;}if(Degree[i]==0&&!visited[i]) s.push(i);   }} if(count!=t) cout<<"图中存在环,该排序不是拓扑排序"<<endl; }int main(){int n,e;cout<<"拓扑排序测试,请输入顶点数和边数"<<endl; cin>>n>>e;DAG d[n];InitGraph(n);cout<<"请输入边的信息"<<endl;    for(int i=0;i<e;++i)    {         cin>>d[i].w1>>d[i].w2>>d[i].weight;    }     MakeGraph(d,e);    cout<<"拓扑排序结果"<<endl;     TopSort(n);                 //system("pause");return 0;}