zoukankan      html  css  js  c++  java
  • 题解 [USACO Mar08] 奶牛跑步

    [USACO Mar08] 奶牛跑步

    Description

    Bessie准备用从牛棚跑到池塘的方法来锻炼. 但是因为她懒,她只准备沿着下坡的路跑到池塘,然后走回牛棚.

    Bessie也不想跑得太远,所以她想走最短的路经. 农场上一共有M(1<=M<=10,000)条路,每条路连接两个用1..N(1<=N<=1000)标号的地点. 更方便的是,如果X>Y,则地点X的高度大于地点Y的高度. 地点N是Bessie的牛棚;地点1是池塘.

    很快, Bessie厌倦了一直走同一条路.所以她想走不同的路,更明确地讲,她想找出K(1<=K<=100)条不同的路经.为了避免过度劳累,她想使这K条路径为最短的K条路径.

    请帮助Bessie找出这K条最短路经的长度.你的程序需要读入农场的地图, 一些从Xi到Yi的路径和它们的长度(Xi,Yi,Di).
    所有(Xi,Yi,Di) 满足( 1<=Yi<Xi; Yi<Xi<=N, 1<=Di<=1,000,000 ).

    Input

    第1行: 3个数: N,M,K
    第2..M+1行: 第 i+1行包含3个数 Xi,Yi,Di, 表示一条下坡的路.

    Output

    第1..K行: 第i行包含第i最短路径的长度,或−1如果这样的路径不存在.如果多条路径有同样的长度,请注意将这些长度逐一列出.

    Sample Input

    5 8 7
    5 4 1
    5 3 1
    5 2 1
    5 1 1
    4 3 4
    3 1 1
    3 2 1
    2 1 1

    Sample Output

    1
    2
    2
    3
    6
    7
    -1

    Hint

    【样例解释】
    路径分别为(5−1),(5−3−1),(5−2−1),(5−3−2−1),(5−4−3−1),(5−4−3−2−1)

    Source

    动态规划, 图论, A*搜索, k短路

    解析

    今天考试竟然靠自己AC了这道题!!(所以不一定是正解)

    首先,这题的意思很容易理解,

    就是从n到1的路径中,求前k条最短的路径。

    并且由于只能由高到低走,

    所以拓扑排序都省了。

    然后,我们维护一个优先队列q[i]表示能从1走到i点的所有路径:

    priority_queue <int> q[1001];

    然后,从终点1开始递推,

    for(int i=1;i<=n;i++)

    每次枚举i所能到达的点j,再将每次前k短的路加上i,j的距离后加入到q[i]中

    for(int j=head[i];j;j=e[j].to){
        int l=e[j].next;
        for(int t=1;t<=k;t++){
            if(q[l].empty()) break;
            q[i].push(q[l].top()-e[j].w);
            c[++c[0]]=q[l].top();
            q[l].pop();
        }
        for(int t=1;t<=c[0];t++){
            q[l].push(c[t]);
        }
        c[0]=0;
    }

    最后,在从q[n]中输出前k短的路就行了(如果去q[n]为空就输出-1)。

    for(int i=1;i<=k;i++){
        if(q[n].empty()){
            puts("-1");
        }
        else{
            printf("%d
    ",-q[n].top());
            q[n].pop();
        }
    }

    时间复杂度为O(k*m),应该能AC了!

    上AC代码:

    #include <bits/stdc++.h>
    using namespace std;
    
    struct road{
        int next,to,w;
    }e[100001];
    int n,m,k;
    int head[10001],cnt=0;
    int c[100001];
    priority_queue <int> q[1001];
    
    
    void add(int x,int y,int w){
        e[++cnt].to=head[x];
        e[cnt].next=y;
        e[cnt].w=w;
        head[x]=cnt;
    }
    
    int main(){
        scanf("%d%d%d",&n,&m,&k);
        for(int i=1;i<=m;i++){
            int x,y,w;
            scanf("%d%d%d",&x,&y,&w);
            add(x,y,w);
        }
        q[1].push(0);
        for(int i=1;i<=n;i++){
            for(int j=head[i];j;j=e[j].to){
                int l=e[j].next;
                for(int t=1;t<=k;t++){
                    if(q[l].empty()) break;
                    q[i].push(q[l].top()-e[j].w);
                    c[++c[0]]=q[l].top();
                    q[l].pop();
                }
                for(int t=1;t<=c[0];t++){
                    q[l].push(c[t]);
                }
                c[0]=0;
            }
        }
        for(int i=1;i<=k;i++){
            if(q[n].empty()){
                puts("-1");
            }
            else{
                printf("%d
    ",-q[n].top());
                q[n].pop();
            }
        }
        return 0;
    }
  • 相关阅读:
    CS224n, lec 10, NMT & Seq2Seq Attn
    CS231n笔记 Lecture 11, Detection and Segmentation
    CS231n笔记 Lecture 10, Recurrent Neural Networks
    CS231n笔记 Lecture 9, CNN Architectures
    CS231n笔记 Lecture 8, Deep Learning Software
    CS231n笔记 Lecture 7, Training Neural Networks, Part 2
    pytorch坑点排雷
    Sorry, Ubuntu 17.10 has experienced an internal error
    VSCode配置python插件
    tmux配置与使用
  • 原文地址:https://www.cnblogs.com/zsq259/p/10484544.html
Copyright © 2011-2022 走看看