拓扑排序

在图中用顶点表示活动,用弧表示活动间的优先关系,这样的有向图成为AOV网。

下面是AOV网的拓扑排序,可以用来检验类似:工程之间有约束关系的,检验看工程的安排是否合理;课程之间有约束的,课程的前后顺序安排是否合理,这就是拓扑排序的一个应用。

文件"topo.h"

#include<iostream> #include<string> #include<queue> using namespace std; const int MAX_VEX_NUM=20; class ArcNode //表结点 { public: int adjvex; ArcNode *nextarc; }; class VNode //头结点 { public: string data; int indegree; ArcNode *firstarc; }; class ALGraph { private: VNode vertices[MAX_VEX_NUM]; int arcnum; int vexnum; public: void Create_ALG() { //构造有向图 string v1,v2; int i,j; ArcNode *p=NULL; cout<<"输入顶点数和边数:"; cin>>vexnum>>arcnum; cout<<"输入顶点名称:"; for(i=0;i<vexnum;i++) { cin>>vertices[i].data; vertices[i].firstarc=NULL; vertices[i].indegree=0; } for(int k=0;k<arcnum;k++) { cout<<"按照尾->头的顺序输入每条边对应的两个顶点:"; cin>>v1>>v2; i=Locate_Vex(v1); j=Locate_Vex(v2); while(i==-1 || j==-1) { cout<<"输入的顶点错误,重新输入:"; cin>>v1>>v2; i=Locate_Vex(v1); j=Locate_Vex(v2); } p=new ArcNode; p->adjvex=j; p->nextarc=vertices[i].firstarc; vertices[i].firstarc=p; vertices[j].indegree+=1; //作为有向弧的头的顶点入度加1 } cout<<"图构造完成"<<endl; } int Locate_Vex(string v) { for(int k=0;k<vexnum && vertices[k].data!=v;k++); if(k<vexnum) return k; else return -1; } /*拓扑排序*/ /*------------------------------------------------ / 对AOV网进行拓扑排序的方法是: / (1)在有向图中选取一个没有前驱的顶点,将其输出 / (2)从图中删除该顶点和所有以他为尾的弧 / 重复上述2个步骤,若有向图中全部顶点都被输出,则 / 該图不存在环,否则,該图存在有向环路。 / 为了实现以上操作,可增加一个记录顶点入度的数据成员, / 每个顶点的入度随着顶点的输出动态变化,入度为0即 / 该顶点没有前驱,删除以该顶点为尾的弧也可以通过将 / 与之相连的顶点的入度都减少1即可。为了减少重复检测 / 入度为0的结点,这里借助队列来装入度为0的顶点,在队列 / 非空时进行入度为0的顶点的出入队和输出,详细操作看代码 /------------------------------------------------*/ void Topo_Sort() { queue<int> s; ArcNode *p=NULL; for(int i=0;i<vexnum;i++) if(!vertices[i].indegree) s.push(i); int count=0; while(!s.empty()) { int k=s.front(); s.pop(); cout<<vertices[k].data<<" "; count++; for(p=vertices[k].firstarc;p;p=p->nextarc) { int w=p->adjvex; if(vertices[w].indegree) vertices[w].indegree--; if(!vertices[w].indegree) s.push(w); } } if(count<vexnum) cout<<"图中含有有向环"<<endl; } };

主函数"main.cpp"

#include"topo.h" int main() { ALGraph G; G.Create_ALG(); cout<<"拓扑排序为:"; G.Topo_Sort(); cout<<endl; return 0; }

测试结果:

输入顶点数和边数:5 6 输入顶点名称:v1 v2 v3 v4 v5 按照尾->头的顺序输入每条边对应的两个顶点:v3 v5 按照尾->头的顺序输入每条边对应的两个顶点:v3 v1 按照尾->头的顺序输入每条边对应的两个顶点:v4 v5 按照尾->头的顺序输入每条边对应的两个顶点:v4 v2 按照尾->头的顺序输入每条边对应的两个顶点:v2 v1 按照尾->头的顺序输入每条边对应的两个顶点:v1 v5 图构造完成 拓扑排序为:v3 v4 v2 v1 v5 Press any key to continue

按照输入生成的有向图如下:

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值