#include "stdio.h"
#include "stdlib.h"
#define MAXNUM 100
//两全局变量提供拓扑排序使用
int visited[MAXNUM];
int inDegree[MAXNUM];
/*输入有向图的数据,输出该有向图的拓扑序列
test data 5 4 0 4 2 4 3 3 1 0 3 2 0 2 3 2 1 0 1 -1 -1
input V4 V2 V0 V3 V1
*/
//有向图的结构体
typedef struct
{
int vexnum;
int arcs[MAXNUM][MAXNUM];
}MGraph,*PMGraph;
void initGraph(PMGraph *p)
{
int n,i,j;
*p =(PMGraph)malloc(sizeof(MGraph));
scanf("%d",&n);
//判定N
(*p)->vexnum=n;
//初始化矩阵
for(i=0;i<n;i++)for(j=0;j<n;j++)(*p)->arcs[i][j]=0;
scanf("%d%d",&i,&j);
while(i!=-1&&j!=-1){
(*p)->arcs[i][j]=1;
scanf("%d%d",&i,&j);
}
}
//我的拓扑排序
void topSort(PMGraph p,int i,int *count)
{
//输出变量结果
int j;
printf("V%d ",i);
//标示i节点已访问
visited[i]=1;
//改变输出后的节点入度信息 即去掉i到j的度
for(j=0;j<p->vexnum;j++)
{
if(p->arcs[i][j]==1)inDegree[j]--;
if(!visited[j]&&inDegree[j]==0)
{
*count++;
topSort(p,j,count);
}
}
}
void topTraver(PMGraph p)
{
int i,j;
int count=0;//判定是否有环
//初始化全局变量
for(i=0;i<p->vexnum;i++)
{
visited[i]=0;inDegree[i]=0;
}
//计算每个节点的入度
for(i=0;i<p->vexnum;i++)
{
for(j=0;j<p->vexnum;j++)
{
if(p->arcs[j][i]==1)inDegree[i]++;
}
}
for(i=0;i<p->vexnum;i++)
{
if(!visited[i]&&inDegree[i]==0)
{
count++;
topSort(p,i,&count);
}
}
if(count<p->vexnum)printf("youhuan\n");
}
//北大老师的拓扑排序 能判定图中有环
void topSort1(PMGraph g)
{
int s=-1,i,j,count=0;
//初始化全局变量
for(i=0;i<g->vexnum;i++)
{
visited[i]=0;inDegree[i]=0;
}
//计算每个节点的入度
for(i=0;i<g->vexnum;i++)
{
for(j=0;j<g->vexnum;j++)
{
if(g->arcs[j][i]==1)inDegree[i]++;
}
}
//通过count判定图中是否有环 紧紧判定入度的节点都大于0,是不合适的 例如 4 0 1 1 2 2 3 3 1 -1 -1
for(i=0;i<g->vexnum;i++)
if(inDegree[i]==0)
{
inDegree[i]=s;
s=i;
}
while(s!=-1)//s为访问节点值
{
printf("V%d ",s);
count++;
i=s;
s=inDegree[s];
//访问节点过后,相邻节点入度减一
for(j=0;j<g->vexnum;j++)
if(g->arcs[i][j])
{
inDegree[j]--;
if(inDegree[j]==0)
{
inDegree[j]=s;s=j;
}
}
}
printf("count=%d\n",count);
if(count<g->vexnum)printf("有环\n");
}
void main()
{
PMGraph p;
initGraph(&p);
//topSort1(p);
topTraver(p);
}
分享到:
相关推荐
在编程实现时,可以设计一个函数,该函数接受一个有向图和一个当前的拓扑序列,然后递归地尝试添加下一个节点。当所有节点都添加完成后,就得到了一个合法的拓扑序列。通过调用这个函数并记录所有结果,我们可以得到...
对于有向图,若发现它是有环的,那么输出它的环,否则,就输出它的拓扑排序
标题中的“判断一个有向图中是否存在回路,并进行输出(拓扑算法)”涉及到的是图论中的一个重要问题,即如何检测有向无环图(DAG,Directed Acyclic Graph)与有向图中的环。这个问题在计算机科学的多个领域都有...
有向图的拓扑排序是图论中的一个重要概念,它主要应用于计算机科学,尤其是在数据结构和算法设计中。拓扑排序是对有向无环图(DAG,Directed Acyclic Graph)进行的一种线性排序,其结果是使得对于图中每条有向边 (u...
主函数一般接收用户输入或读取文件,构建有向图,然后调用拓扑排序算法,输出排序结果。 5、有向图举例: 通过实例来展示有向图的不同表示方法,如邻接矩阵和邻接表,并演示如何进行拓扑排序。 总的来说,有向图的...
根据提供的文档信息,本次课程设计的主要任务是设计并实现一个程序来输出给定有向无环图(DAG)的所有可能的拓扑排序序列。为了完成这个任务,我们需要明确几个关键点: ### 1. 课程设计内容与要求 #### 1.1 基本...
键盘输入数据,建立一个有向图的邻接表,并输出该邻接表;在有向图的邻接表的基础上计算各顶点的度,并输出;以有向图的邻接表为基础实现并输出它的拓扑排序序列;
如果边是有方向的,即从一个顶点指向另一个顶点,那么这个图就被称为有向图。无环图意味着图中不存在任何从一个顶点出发经过若干边后又回到原点的路径。DAG是这两个特性的结合,即图中所有边都是有向的,且不存在环...
在图论中,拓扑序列是指有向图中的一个序列,其中每个顶点的入度为0或1。拓扑序列的应用非常广泛,例如在编译器设计、项目管理、数据分析等领域。 二、代码解释 在给定的代码中,我们可以看到作者定义了一些宏和...
在C#中实现数据结构课程设计,特别是有向图的拓扑排序,主要涉及以下几个核心概念和技术: 1. **有向图(Directed Graph)**:有向图是一种特殊的图,其中的边是有方向的,表示从一个顶点到另一个顶点的单向连接。...
在压缩包文件"有向图的强连通分量"中,可能包含了具体的代码实现或测试数据,通过阅读和分析这些内容,可以更直观地理解上述算法的细节。此外,还可以将找到的强连通分量输出到文件中,方便进一步的分析和处理。 ...
任意给定一个有向图,设计一个算法,对它进行拓扑排序。拓扑排序算法思想:a.在有向图中任选一个没有前趋的顶点输出;b.从图中删除该顶点和所有以它为尾的弧;c.重复上述a、b,直到全部顶点都已输出,此时,顶点输出...
拓扑排序是对有向无环图(DAG,Directed Acyclic Graph)的一种排序,其结果是一组顶点的线性序列,使得对于每一条有向边 (u, v),顶点 u 在序列中都出现在顶点 v 之前。拓扑排序可以有多个合法的排序结果,因为不同...
本文将详细讲解如何使用C#语言实现有向图算法,包括邻接表、关键路径、深度优先搜索(DFS)和广度优先搜索(BFS),以及拓扑排序。 首先,我们要理解有向图的概念。有向图是由顶点(节点)和边组成的,边具有方向性...
由于拓扑排序只适用于无环图,因此我们可以利用这个特性来检测有向图中是否存在回路。 以下是实现这个功能的一种常见方法,使用深度优先搜索(DFS)或广度优先搜索(BFS): 1. **深度优先搜索(DFS)**:从任意未...
有向图是由节点(顶点)和有方向的边构成的图,其中的路径指的是沿着边的方向从一个节点移动到另一个节点的序列。 首先,我们要了解有向图的基本概念。有向图用邻接矩阵或邻接表来表示,前者是一个二维数组,后者则...
在有向图中,边是从一个节点指向另一个节点的,而无环表示图中不存在任何起点到终点形成环路的路径。在这样的图中,可以定义一种顺序,使得所有有向边都是从排序靠前的节点指向排序靠后的节点,这就是拓扑序列。 ...
其中,有向图是一种特殊的数据结构,由顶点(节点)和有方向的边组成,表示从一个顶点到另一个顶点的关系。有向图生成树是一种算法,用于从有向图中找到一棵子树,这棵子树包含原图的所有顶点,并且没有环路。这个...
在数据结构领域,有向图可以使用邻接矩阵或邻接表来表示。邻接矩阵是一个二维数组,其中的每个元素表示一对顶点之间是否存在边;如果存在,对应位置的值通常为1,不存在则为0。邻接表则是为每个顶点维护一个列表,...
拓扑排序是图论中的一个重要概念,特别是在有向无环图(DAG,Directed Acyclic Graph)中。在这个数据结构的资源中,你将能够动态地观察和理解拓扑排序的过程。拓扑排序是对有向无环图的顶点的一种线性排序,使得...