java实现AOV图的拓扑排序

拓扑排序作为图的应用,了解拓扑排序必须首先了解AOV图。

AOV网表示一个有向图中顶点,用弧表示顶点之间的优先关系。如下图所示,在AOV网中,若从顶点vi到顶点vj之间存在一条有向路径,则称顶点vi为顶点vj的前驱,顶点vj为顶点vi的后继。注意,AOV图不能有回路,否则会将序列陷入死循环,称为死锁。

进行拓扑排序,一般步骤如下:

<1>在AOV网中选择一个入度为0的顶点

<2>在AOV网中删除此顶点及其相连的有向边

<3>重复步骤<1>和<2>,直到AOV网中没有入度为0的顶点为止

由于拓扑排序具有不确定性,因此经过排序的序列应人而异,不过大多序列的逻辑关系能够走通。

程序如下:

package 拓扑排序;
/*
 * 在AOV网中寻找拓扑排序序列的步骤如下:
 * <1>在AOV网中选择一个入度为0的顶点
 * <2>从AOV往中删除此顶点以及与其相连的有向边
 * <3>重复步骤<1>和<2>。直到AOV网中没有入度为0的顶点
 */
public class TopoSort {
 /**
  * @author 刘雁冰
  * @date 2015-02-14 20:22
  */
 
 /*
  * Max:定义顶点的最大容量为100
  * ver:使用内部Vertexs类创建一个数组ver,存储顶点的关键字
  * map:AOV网的邻接矩阵表
  * n:顶点的数量
  * topoSort:存储最终得到的序列
  */
 static int Max=100;
 static Vertexs ver[];
 static int map[][];
 static int n;
 static char topoSort[];
 
 public static void main(String[] args) {
  // TODO Auto-generated method stub
  ver=new Vertexs[Max];
  map=new int[Max][Max];
  n=0;
  topoSort=new char[Max];
  //初始化邻接矩阵
  for(int i=0;i<Max;i++){
   for(int j=0;j<Max;j++){
    map[i][j]=0;
   }
  }
  TopoSort ts=new TopoSort();
  //读入AOV网顶点的关键字
  ts.addVertex(‘A‘);
  ts.addVertex(‘B‘);
  ts.addVertex(‘C‘);
  ts.addVertex(‘D‘);
  ts.addVertex(‘E‘);
  ts.addVertex(‘F‘);
  ts.addVertex(‘G‘);
  ts.addVertex(‘H‘);
  ts.addVertex(‘I‘);
  ts.addVertex(‘J‘);
  ts.addVertex(‘K‘);
  ts.addVertex(‘L‘);
  
  //读入AOV网边的连接信息,由于是有向图,只需读入一次
  ts.addEdge(0, 1);
  ts.addEdge(0, 3);
  ts.addEdge(0, 10);
  ts.addEdge(1, 10);
  ts.addEdge(2, 3);
  ts.addEdge(2, 4);
  ts.addEdge(2, 5);
  ts.addEdge(3, 7);
  ts.addEdge(5, 7);
  ts.addEdge(5, 6);
  ts.addEdge(5, 8);
  ts.addEdge(6, 8);
  ts.addEdge(6, 9);
  ts.addEdge(10, 11);
  ts.addEdge(11, 9);
  ts.addEdge(11, 6);
  
  ts.topoSort();
 }
 
 //构造顶点关键字数组
 public void addVertex(char v){
  ver[n++]=new Vertexs(v);
 }
 
 //构造边的邻接矩阵
 public void addEdge(int start,int end){
  map[start][end]=1;
 }
 
 public void topoSort(){
  //num:顶点数量n要进行递减,因此起始存入num,作为输出序列遍历使用
  //isEdge:判定该边是否相连
  int num=n;
  boolean isEdge;
  
  while(n>0){
   //选取一个入度为0的顶点
   int currVer=0;
   //遍历邻接矩阵
   for(int row=0;row<n;row++){
    isEdge=false;
    for(int col=0;col<n;col++){
     if(map[row][col]>0)
      isEdge=true;
    }
    //抽取邻接边表中没有出度的顶点(将邻接表行数赋值给当前顶点)
    if(!isEdge)
     currVer=row;
   }
   //将没有出度的顶点存入序列结果最后的位置
   topoSort[n-1]=ver[currVer].value;
   
  /*
   *  删除顶点操作
   * 当前顶点不为最后顶点时进行
   */
   if(currVer!=n-1){
    //顶点关键字数组往后移动一位
    for(int i=currVer;i<n;i++)
     ver[i]=ver[i+1];
    
    /*
     * 移动邻接表行列,覆盖原值
     */
    //邻接表行数往后移动一位(向右移动)
    for(int row=currVer;row<n-1;row++)
     for(int col=0;col<n;col++)
      map[row][col]=map[row+1][col];
    //邻接表列数往后移动一位(向左移动)
    for(int col=currVer;col<n-1;col++)
     for(int row=0;row<n;row++)
      map[row][col]=map[row][col+1];
   }
   n--;   //下一个顶点
  }
  
  //输出结果
  System.out.println("该图的拓扑排序序列为:");
  for(int i=0;i<num;i++){
  }
 }
}
class Vertexs{
 public char value;
 public Vertexs(char v){
  value=v;
 }
}

测试结果如下:

时间: 2024-10-29 10:46:49

java实现AOV图的拓扑排序的相关文章

有向无环图(DAG)拓扑排序的两种方法

如下图的DAG: 第一种: (1)从AOV网中选择一个没有前驱的顶点并且输出它: (2)从AOV网中删除该顶点,并且上去所有该顶点为尾的弧: (3)重复上述两步,直到全部顶点都被输出,或者AOV网中不存在没有前驱的顶点. 第二种: 使用深度优先搜索(DFS),并标记每一个节点的第一次访问(pre)和最后一次访问时间(post),最后post的逆序就是DAG的拓扑排序,其实也是节点在进行DFS搜索时,出栈的逆序就是拓扑排序. 拓扑序列的结果有: (1) c++,高等数学,离散数学,数据结构,概率论

DAG图的拓扑排序 python

在DAG中DFS中顶点的出栈顺序即逆拓扑序. def topological_sort( graph ): is_visit = dict( ( node, False ) for node in graph ) li = [] def dfs( graph, start_node ): for end_node in graph[start_node]: if not is_visit[end_node]: is_visit[end_node] = True dfs( graph, end_n

图的拓扑排序

定义: 图的拓扑排序是对有向无环图来说的,无向图和有环图没有拓扑排序,或者说不存在拓扑排序,对于一个有向无环图G进行拓扑排序,是将G中所有顶点排成一个线性序列,使得图中任意一对顶点u和v,若图G存在边< u, v >,则u在线性序列中出现在v之前.对一个有向无环图进行拓扑排序产生的线性序列称为满足拓扑次序的序列.一个有向无环图可以表示某种动作或者方案,或者状态,而有向无环图的拓扑序列通常表示某种某案切实可行或者各个成员之间的某种关系. 举个栗子,看上面那个图,v1v2v3v4v5v6v7v8是

有向无环图的应用—AOV网 和 拓扑排序

有向无环图:无环的有向图,简称 DAG (Directed Acycline Graph) 图. 一个有向图的生成树是一个有向树,一个非连通有向图的若干强连通分量生成若干有向树,这些有向数形成生成森林. 在工程计划和管理方面的应用 除最简单的情况之外,几乎所有的工程都可分为若干个称作“活动”的子工程,并且这些子工程之间通常受着一定条件的约束,例如:其中某些子工程必须在另一些子工 程完成之后才能开始.对整个工程和系统,人们关心的是两方面的问题: 一是工程能否顺利进行,即工程流程是否“合理”: 二是

【图】拓扑排序

参考CSDN拓扑排序的原理及Java实现 拓扑排序C++实现 拓扑排序百度百科 若不是上了学堂在线的数据结构课程,我估计今后不做技术的话,都接触不到图的拓扑排序这个概念了.先是看了百度百科的解释,拓扑排序现实中的应用是选课,即某些课程需要一些先修课程的学习后才适合上.比如数据结构的学习,是离散数学.编程语言,后者是前者的先修课程. 拓扑排序定义:将有向无环图DAG中的顶点以线性方式进行排序.即对于任何连接自顶点u到顶点v的有向边uv,在最后的排序结果中,顶点u总是在顶点v的前面. 1.创建图:

图的邻接表表示与无环图的拓扑排序

一.  图的最常用的表示方法是邻接矩阵和邻接表. 1,邻接矩阵 邻接矩阵其实就是一个二维数组,对于每条边<u,v>,我们就令A[u][v] = 1,如果图为有权图,我们也可以令A[u][v]等于该权,这么表示的优点是非常简单,但是它的空间需求很大,如果图是稠密的,邻接矩阵是合适的表示方法,如果图是稀疏的,那这种方法就太浪费空间了,下面给出图的邻接矩阵表示例子. 2 邻接表 邻接表是图的常用储存结构之一.邻接表由表头结点和表结点两部分组成,其中图中每个顶点均对应一个存储在数组中的表头结点.如下图

图的拓扑排序(转)

一.概述 对一个有向无环图(Directed Acyclic Graph简称DAG)G进行拓扑排序,是将G中所有顶点排成一个线性序列,使得图中任意一对顶点u和v,若<u,v> ∈E(G),则u在线性序列中出现在v之前.   通常,这样的线性序列称为满足拓扑次序(TopoiSicai Order)的序列,简称拓扑序列.注意:   ①若将图中顶点按拓扑次序排成一行,则图中所有的有向边均是从左指向右的.   ②若图中存在有向环,则不可能使顶点满足拓扑次序.   ③一个DAG的拓扑序列通常表示某种方案

图的拓扑排序、关键路径、最短路径算法 -- C++实现

一:拓扑排序 对一个有向无环图(Directed Acyclic Graph简称DAG)G进行拓扑排序,是将G中所有顶点排成一个线性序列,使得图中任意一对顶点u和v,若边(u,v)∈E(G),则u在线性序列中出现在v之前.通常,这样的线性序列称为满足拓扑次序(Topological Order)的序列,简称拓扑序列. 拓扑排序就是要找到入度为0的顶点,并依次压栈.首先将栈顶顶点输出,删除以此顶点为弧尾的顶点,并更新其他顶点的入度.若入度为0,则继续压栈.更新完毕继续出栈,直至栈空.元素出栈并输出

我对图的拓扑排序理解

// 节点结构定义,u表示边的始点,v表示边的尾点, node指向下一个可能的节点 var node = {u : 0, v : 0, node : null}; var top = -1; // 游标指针 var ind = []; // 记录入度数组 // 邻接表 arr = [node, ...] var aov = function(arr) { // 1. 初始化 记录入度 的数组 var len = arr.length; for(var i = 0; i < len; i++) {