zoukankan      html  css  js  c++  java
  • K-th Path

    原题解链接戳这里

    校内训练赛的T1...

    简单说一下题意:

    有n个点,m条边的无向图。某两点间将可以有一个最短路径。不同组合(vi,vj)的最短路径中,输出第k小的最短路径长度。

    n<=2e5。

    显而易见,暴力跑算法是不可取的。注意到k很小,可以考虑重新构图。

    我们可以取出图中前k小的路,再以这些路径所连接的点重新构造一张小图。则小图的v<=400。轻轻松松Floyd。

    可以感性证明一下子:这k小路径构成的点,互相之间的最短路径也一定是在原图中前k小。缩短路径规模就可以轻松跑算法了

    我们把边连接的点取出来后,unique一下,去重。因为可能连接的点有(1,2)(2,3),我们只需要123。

    然后利用lower_bound抛弃选出来的点在原图中的编号,直接给予新的编号。反正最后只需要边长无所谓点。

    不要忘记longlong。

    #include <iostream>
    #include <cstdio>
    #include <algorithm>
    #define R register
    #define N 200005
    typedef long long ll;
    long long INF=1ll<<60;
    using namespace std;
    int n,m,k,b[1000],cnt,cnt1;
    long long mp[805][805],d[N];
    struct node{int u,v,w;}a[N];
    bool cmp(node x,node y){return x.w<y.w;}
    inline int ri(){
        char c=getchar();int x=0,w=1;
        while(!isdigit(c)){if(c=='-')w=-1;c=getchar();}
        while( isdigit(c)){x=(x<<3)+(x<<1)+c-48;c=getchar();}
        return x*w;
    }
    int main(){
        n=ri(),m=ri(),k=ri();
        for(R int i=1;i<=m;i++)
            a[i].u=ri(), a[i].v=ri(), a[i].w=ri();
        sort(a+1,a+m+1,cmp);
        for(R int i=1;i<=min(m,k);i++) 
            b[++cnt]=a[i].u, b[++cnt]=a[i].v;
        sort(b+1,b+cnt+1);
        cnt=unique(b+1,b+cnt+1)-b-1;
        for(R int i=1;i<=cnt;i++)
            for(R int j=1;j<=cnt;j++)
                mp[i][j]=INF;
        for(R int i=1;i<=min(m,k);i++){
            int u=lower_bound(b,b+cnt+1,a[i].u)-b;
            int v=lower_bound(b,b+cnt+1,a[i].v)-b;
            mp[u][v]=mp[v][u]=a[i].w;
        }
        for(R int q=1;q<=cnt;q++)
            for(R int i=1;i<=cnt;i++)
                for(R int j=1;j<=cnt;j++)
                    if(mp[i][j]>mp[i][q]+mp[q][j])
                        mp[i][j]=mp[i][q]+mp[q][j];
        for(R int i=1;i<=cnt;i++)
            for(R int j=i+1;j<=cnt;j++)
                if(mp[i][j]!=INF)d[++cnt1]=mp[i][j];
        sort(d,d+cnt1+1);
        printf("%lld
    ",d[k]);
        return 0;
    }
  • 相关阅读:
    多线程demo
    my parnter code review
    my code review
    思考题
    数组中最大子数组的和
    TestForGit
    say Hellow的测试类及测试结果
    读《Build To Win》感想
    随机生成300道四则运算
    思考题 程序员本计划在三天内完成任务,但在第三天的下午他发现了自己程序的弱点,他在想是否是自己采取另一种方法去解决它,但是需要额外的时间。如若反之,则会在后期团队会在集成方面花费时间。该怎么办?
  • 原文地址:https://www.cnblogs.com/flicker-five/p/11598188.html
Copyright © 2011-2022 走看看