zoukankan      html  css  js  c++  java
  • SDUT 2498 数据结构实验之图论十一:AOE网上的关键路径

     

    数据结构实验之图论十一:AOE网上的关键路径

    Time Limit: 2000 ms Memory Limit: 65536 KiB

    Problem Description

        一个无环的有向图称为无环图(Directed Acyclic Graph),简称DAG图。
        AOE(Activity On Edge)网:顾名思义,用边表示活动的网,当然它也是DAG。与AOV不同,活动都表示在了边上,如下图所示:
                                         
        如上所示,共有11项活动(11条边),9个事件(9个顶点)。整个工程只有一个开始点和一个完成点。即只有一个入度为零的点(源点)和只有一个出度为零的点(汇点)。
        关键路径:是从开始点到完成点的最长路径的长度。路径的长度是边上活动耗费的时间。如上图所示,1 到2 到 5到7到9是关键路径(关键路径不止一条,请输出字典序最小的),权值的和为18。

    Input

        这里有多组数据,保证不超过10组,保证只有一个源点和汇点。输入一个顶点数n(2<=n<=10000),边数m(1<=m <=50000),接下来m行,输入起点sv,终点ev,权值w(1<=sv,ev<=n,sv != ev,1<=w <=20)。数据保证图连通。

    Output

        关键路径的权值和,并且从源点输出关键路径上的路径(如果有多条,请输出字典序最小的)。

    Sample Input

    9 11
    1 2 6
    1 3 4
    1 4 5
    2 5 1
    3 5 1
    4 6 2
    5 7 9
    5 8 7
    6 8 4
    8 9 4
    7 9 2

    Sample Output

    18
    1 2
    2 5
    5 7
    7 9

    提示:该题的知识点是AOE关键路径,而AOE关键路径的特点就是不管是从前往后找还是从后往前更新,结点的权值都是不变一条路径。

    代码实现如下(g++):
    #include<bits/stdc++.h>
    #define N 500500
    
    using namespace std;
    
    struct node
    {
        int va,vb,w;
    } dian[N];
    
    int path[N],dut[N],in[N],out[N],ans;
    
    void AOE(int n,int m)//AOE关键路径就是找从前往后更新的各点权值和从后往前更新的各点权值一样的点的路径即为关键路径
    {
        memset(path,0,sizeof(path));
        memset(dut,0,sizeof(dut));
        for(int j=2; j<=n; j++)
        {
            int temp=0;
            for(int i=1; i<=m; i++)
            {
                if((dut[dian[i].va]<dut[dian[i].vb]+dian[i].w)||(dut[dian[i].va]==dut[dian[i].vb]+dian[i].w&&dian[i].vb<path[dian[i].va]))//不断更新各结点的权值
                {
                    dut[dian[i].va]=dut[dian[i].vb]+dian[i].w;//找到各结点权值最大的一条路
                    path[dian[i].va]=dian[i].vb;//记录下从前边点到的后边点的路径
                    temp=1;
                }
            }
            if(!temp)
                break;
        }
        printf("%d
    ",dut[ans]);
        int k=ans;
        while(path[k]!=0)
        {
            printf("%d %d
    ",k,path[k]);
            k=path[k];
        }
    }
    
    
    
    int main()
    {
        int n,m,i,a,b,c;
        while(~scanf("%d %d",&n,&m))
        {
            memset(dian, 0, sizeof(dian));
            memset(in, 0, sizeof(in));
            memset(out, 0, sizeof(out));
            for(i=1; i<=m; i++)
            {
                scanf("%d %d %d",&a,&b,&c);
                dian[i].va=a;
                dian[i].vb=b;
                dian[i].w=c;
                in[a]++;
                out[b]++;
            }
            for(i=1; i<=n; i++)
            {
                if(out[i]==0)
                {
                    ans=i;//记录最后一个点的位置
                }
            }
            AOE(n,m);
        }
        return 0;
    }
    
    
    /***************************************************
    Result: Accepted
    Take time: 796ms
    Take Memory: 1640KB
    ****************************************************/
  • 相关阅读:
    AVL树插入操作InsertAVL的实现
    epoll中EPOLLSHOT的使用
    LeetCode79:单词搜索,以及在传参时使用引用传递的重要性
    Muduo中MutexLock类中嵌套UnassignGuard类的作用
    LeetCode84:柱状图中最大的矩形
    计算图的关节点
    迪杰斯特拉算法与佛洛依德算法
    二叉树的后序遍历,先序,中序
    最近一段的学习计划
    串:KMP算法
  • 原文地址:https://www.cnblogs.com/jkxsz2333/p/9508002.html
Copyright © 2011-2022 走看看