当前位置: 首页 > news >正文

C++ AOV 拓扑排序

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档

文章目录

  • 前言
  • 一、AOV是什么?
  • 二、拓扑排序
  • 三、代码实现


前言

本文主要记录AOV算法的实现。

图论中将图分为有向图与无向图,同时还可以根据是否有回路分为有环图与无环图。

软考中级经常会考到若干关于工期的安排问题:
在这里插入图片描述
上面的图就是一个有向无环图(DAG)


一、AOV是什么?

AOV首先是一个DAG,然后在这个图中,顶点用来表示活动(Active on vertices)并利用边u->v来表示u是v的先决条件(v依赖u),同时具有传递性(u是v的先决,v是w的先决,那么u也算是w的先决)。正是因为这个依赖传递,如果存在u->v v->w w->u,就会推出u->u也就是u依赖他自己,这个是不行的。学术化一点就是反自反性,这也是为什么AOV必须是一个有向无环图DAG。

二、拓扑排序

基于AOV网格,可以完成拓扑排序,将AOV网格中的节点存到一个列表中,保证在AOV中u->v,在列表中u会存放在v的前面(不一定是挨着的)

算法思路:

1.遍历AOV网格,寻找所有入度为0的节点,并放入一个容器中
2.从容器中拿出一个入度为0的节点,将所有与该节点相邻的节点的边删除(物理层面上也可以不删除),并给他们的入度减小1(这个必须要做)
3.同时判断“删除”边后,是否有新的节点入度为0,如果有就放入到容器中
4.循环上面2 3 的过程,直到容器没有节点。此时可以判断如果还有节点的入度不为0,就代表当前图有环。反之则代表拓扑排序成功结束

三、代码实现

#include <iostream>
#include <stack>
using std::cin;
using std::cout;
using std::stack;const int MAXN = 100;// 边节点
struct ArcNode{int no;ArcNode *next;ArcNode(){}ArcNode(int no){this->no = no;next = nullptr; }
};//顶点节点
struct VNode
{int no;// 当前节点的入度int indegree;ArcNode* firstArc;VNode(){no = -1;indegree = 0;firstArc = nullptr;}VNode(int no, int indegree, ArcNode* firstArc){this->no = no;this->indegree = indegree;this->firstArc = firstArc;}// 头插法将边界点插入到顶点节点下面void insert(ArcNode* node){node->next = this->firstArc;this->firstArc = node;}~VNode(){}
};//领接表
struct ADGList
{VNode v[MAXN];int vexnum,arcnum;ADGList(){for(int i = 0; i < MAXN; i ++){v[i].no = i;}}void print(){for(int i = 0; i < vexnum; i ++){ArcNode* p = v[i].firstArc;while(p != nullptr){cout << p->no << " -->  ";p = p->next;}cout << "NULL\n";}}
};void createAGDList(ADGList& adglist){int vnum,arcnum; // 顶点数  边数int u,v; // 用于表示每一条边的起点终点cin >> vnum >> arcnum;adglist.vexnum = vnum;adglist.arcnum = arcnum;for(int i = 0; i < arcnum; i ++){cin >> u >> v;adglist.v[u].insert(new ArcNode(v));adglist.v[v].indegree ++;}
}void topoSort(ADGList& adglist){std::deque<int> zero_ind_q,ans_q;// 将领接表中入度为0的顶点节点压入到栈中int n = adglist.vexnum;for(int i = 0; i < n; i ++){if(adglist.v[i].indegree == 0){zero_ind_q.push_back(i);}}while(!zero_ind_q.empty()){int zero_ind_node = zero_ind_q.front();zero_ind_q.pop_front();ans_q.push_back(zero_ind_node);ArcNode* p = adglist.v[zero_ind_node].firstArc;while(p != nullptr){adglist.v[p->no].indegree --;if(adglist.v[p->no].indegree == 0){zero_ind_q.push_back(p->no);}p = p->next;} // cout << "zero_ind_q.size is" << zero_ind_q.size() << "\n";   }cout << "topoSort done!\n";while(!ans_q.empty()){int front = ans_q.front();ans_q.pop_front();cout << front << " ";}}int main(int argc, const char** argv) {ADGList adglist;createAGDList(adglist);adglist.print();topoSort(adglist);return 0;
}
http://www.dtcms.com/a/348810.html

相关文章:

  • pyecharts可视化图表-scatter:从入门到精通
  • 2020/12 JLPT听力原文 问题二 5番
  • 【网络运维】Shell 脚本编程:case 条件语句
  • 【大语言模型 18】Vision Transformer革命解析:图像理解的范式突破与架构创新
  • VsCode使用SFTP连接Linux
  • 油雾干扰下误报率↓76%!陌讯动态感知算法在卸油作业安全识别中的实战突破
  • Java:HashSet的使用
  • 【MySQL】CRUD基础详解
  • 基于 Redis + JWT 的跨系统身份共享方案
  • HTTP数据之旅:一个网络请求的完整冒险
  • Unity的Cursor.lockState
  • 油雾环境下漏检率↓79%!陌讯多模态检测算法在加油站智能巡检的落地实践
  • VMware Workstation 不可恢复错误:(vcpu-0)
  • 强反射场景漏检率↓89%!陌讯动态感知算法在护目镜合规检测的实战解析
  • 二叉树学习笔记
  • MyBatis 和 MyBatis-Plus对比
  • 【GEE+Python 实战】用 Sentinel-2 监测 2024 年研究区 NDVI 变化(附完整源码与避坑指南)
  • 深入解析十大经典排序算法原理与实现
  • 理想汽车智驾方案介绍 2|MindVLA 方案详解
  • Java 编译器的世界:前端、JIT 与 AOT 的秘密:详解 Java 的编译过程与编译器生态
  • 秦始皇在位时的重要贡献
  • 室联人形机器人:家政服务任务结构化、技术要点、深入应用FPGA的控制系统框架设计(整合版A)
  • Redis 启动的三种方式:从基础到实战配置指南
  • WSL-linux部署IndexTTS 记录(含本地 CUDA/cuDNN 编译依赖说明)
  • 深度剖析Spring AI源码(二):Model抽象层 - “驯服”天下AI的“紧箍咒”
  • 《Linux 网络编程二:UDP 与 TCP 的差异、应用及问题应对》
  • Grafana k6 性能测试
  • golang5字符串
  • Linux驱动之DMA(三)
  • 强光干扰下漏检率↓78%!陌讯动态决策算法在智慧交通违停检测的实战优化