1. 程式人生 > >絡谷 P2865 [USACO06NOV]路障Roadblocks

絡谷 P2865 [USACO06NOV]路障Roadblocks

雙向 size cap each ron tin ner ble string

P2865 [USACO06NOV]路障Roadblocks

題目描述

Bessie has moved to a small farm and sometimes enjoys returning to visit one of her best friends. She does not want to get to her old home too quickly, because she likes the scenery along the way. She has decided to take the second-shortest rather than the shortest path. She knows there must be some second-shortest path.

The countryside consists of R (1 ≤ R ≤ 100,000) bidirectional roads, each linking two of the N (1 ≤ N ≤ 5000) intersections, conveniently numbered 1..N. Bessie starts at intersection 1, and her friend (the destination) is at intersection N.

The second-shortest path may share roads with any of the shortest paths, and it may backtrack i.e., use the same road or intersection more than once. The second-shortest path is the shortest path whose length is longer than the shortest path(s) (i.e., if two or more shortest paths exist, the second-shortest path is the one whose length is longer than those but no longer than any other path).

貝茜把家搬到了一個小農場,但她常常回到FJ的農場去拜訪她的朋友。貝茜很喜歡路邊的風景,不想那麽快地結束她的旅途,於是她每次回農場,都會選擇第二短的路徑,而不象我們所習慣的那樣,選擇最短路。 貝茜所在的鄉村有R(1<=R<=100,000)條雙向道路,每條路都聯結了所有的N(1<=N<=5000)個農場中的某兩個。貝茜居住在農場1,她的朋友們居住在農場N(即貝茜每次旅行的目的地)。 貝茜選擇的第二短的路徑中,可以包含任何一條在最短路中出現的道路,並且,一條路可以重復走多次。當然咯,第二短路的長度必須嚴格大於最短路(可能有多條)的長度,但它的長度必須不大於所有除最短路外的路徑的長度。

輸入輸出格式

輸入格式:

Line 1: Two space-separated integers: N and R

Lines 2..R+1: Each line contains three space-separated integers: A, B, and D that describe a road that connects intersections A and B and has length D (1 ≤ D ≤ 5000)

輸出格式:

Line 1: The length of the second shortest path between node 1 and node N

輸入輸出樣例

輸入樣例#1:
4 4
1 2 100
2 4 200
2 3 250
3 4 100
輸出樣例#1:
450

說明

Two routes: 1 -> 2 -> 4 (length 100+200=300) and 1 -> 2 -> 3 -> 4 (length 100+250+100=450)

思路:k短路。

錯因:無。

#include<iostream>
#include<queue>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define MAXN 400000
using namespace std;
struct nond{
    int g,f,to;
    bool operator<(const nond &r) const {
        if(r.f==f)    return r.g<g;
        else return r.f<f;
    }
}tmp,opt;
int n,m,s,t,ans,cnt,tot,tot1;
int dis[MAXN],vis[MAXN];
int to[MAXN],cap[MAXN],net[MAXN],head[MAXN];
int to1[MAXN],cap1[MAXN],net1[MAXN],head1[MAXN];
int add(int u,int v,int w){
    to[++tot]=v;net[tot]=head[u];cap[tot]=w;head[u]=tot;
    to[++tot]=u;net[tot]=head[v];cap[tot]=w;head[v]=tot;
    to1[++tot1]=v;net1[tot1]=head1[u];cap1[tot1]=w;head1[u]=tot1;
    to1[++tot1]=u;net1[tot1]=head1[v];cap1[tot1]=w;head1[v]=tot1;
}
void spfa(int s){
    queue<int>que1;
    for(int i=0;i<=n;i++)    dis[i]=123456789;
    que1.push(s);
    vis[s]=1;dis[s]=0;
    while(!que1.empty()){
        int now=que1.front();
        que1.pop();
        vis[now]=0;
        for(int i=head1[now];i;i=net1[i])
            if(dis[to1[i]]>dis[now]+cap1[i]){
                dis[to1[i]]=dis[now]+cap1[i];
                if(!vis[to1[i]]){
                    vis[to1[i]]=1;
                    que1.push(to1[i]);
                }
            }
    }
}
int Astar(int k){
    priority_queue<nond>que;
    if(s==t)    k++;
    if(dis[s]==123456789)    return -1;
    tmp.g=0;
    tmp.to=s;
    tmp.f=dis[s];
    que.push(tmp);
    while(!que.empty()){
        tmp=que.top();
        que.pop();
        if(tmp.to==t)    cnt++;
        if(cnt==k)    return tmp.g;
        for(int i=head[tmp.to];i;i=net[i]){
            opt.to=to[i];
            opt.g=tmp.g+cap[i];
            opt.f=opt.g+dis[to[i]];
            que.push(opt);
        }
    }
    return -1;
}
int main(){
    scanf("%d%d",&n,&m);
    for(int i=1;i<=m;i++){
        int x,y,z;
        scanf("%d%d%d",&x,&y,&z);
        add(x,y,z);
    }
    t=n;s=1;
    spfa(t);
    for(int i=1;i<=n;i++){
        cnt=0;
        ans=Astar(i);
        if(ans!=dis[1])
            break;
    }
    printf("%d",ans);
}

絡谷 P2865 [USACO06NOV]路障Roadblocks