【C语言】拓扑排序——求图所有顶点入度及拓扑序列

本文介绍了AOV网的结构,重点阐述了如何通过入度计算和栈数据结构实现拓扑排序,以及如何判断是否存在回路。
摘要由CSDN通过智能技术生成

        AOV网:顶点表示活动,弧表示活动间关系的有向无环图

        拓扑排序即求AOV网的拓扑序列:

  • 输出AOV网中所有入度为0的结点
  • 将当前结点删除并将其所有邻结点的入度减一,再输出所有入度为0的结点
  • 如果输出的结点个数小于图的结点个数,则存在回路,无拓扑序列,否则输出的结点为一个拓扑序列

        求图中各个结点入度:设置入度数组记录各个结点入度,遍历图中的所有结点,若当前结点有邻结点,则更新其邻结点入度数组。

        拓扑排序:利用栈将所有入度为0的结点进栈。如果栈非空则重复如下操作:

  • 栈顶元素出栈并输出
  • 将其所有邻结点的入度减一,如果更新后邻结点入度变为0则入栈

        最后判断输出个数和图中的结点个数即可

void FindID(Graph G,int indegree[]){//求图中各顶点的入度,并记录在数组
	for(int i=0;i<G.vexnum;i++){//初始化入度数组
		indegree[i]=0;
	}
	for(int i=0;i<G.vexnum;i++){//遍历每个结点,若当前结点有邻结点,则更新其邻结点入度数组
		ArcNode* p=G.vertex[i].firstarc;
		while(p!=NULL){
			indegree[p->adjvex]++;
			p=p->nextarc;
		}
		/*邻接矩阵实现:
		int w=FirstAdjVex(G,i);
		while(w!=-1){
			indegree[w]++;
			w=NextAdjVex(G,i,w);	
		}
		*/
	}
}
void TopSort(Graph G){//拓扑排序,输出图G的拓扑序列
	int indegree[MAX_VERTEX_NUM];//入度数组
	int count=0;//统计拓扑序列元素个数,小于图的结点个数则不为AOV网
	FindID(G,indegree);//求顶点入度
	InitStack(&S);//建立并初始化栈S
	for(int i=0;i<G.vexnum;i++){//让所有度为0的结点入栈
		if(indegree[i]==0){
			PUSH(&S,i);
		}
	}
	while(!IsEmpty(S)){//栈非空则栈顶元素出栈并输出
		POP(&S,&v);
		visit(v);
		count++;//更新count值
		ArcNode* p=G.vertex[v].firstarc;
		while(p!=NULL){//更新其邻结点入度数组,如果度变为0则让其入栈
			int k=--indegree[p->adjvex];
			if(k==0){
				PUSH(&S,p->adjvex);
			}
			p=p->nextarc;
		}
	}
	if(count<G.vexnum){
		printf("该图有回路,不为AOV网无拓扑序列\n");
	}
}

        

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值