意思就是费用的最大值最小

那么我们对最大费用进行二分,按此跑最短路,累计扣减血量进行比较即可

 1 #include<cstdio>
 2 #include<cstring>
 3 using namespace std;
 4 const int N=10010,M=100010;
 5 long long n,m,hp,tmp,sum[N],que[N],vis[N],w[N];
 6 int size,head[M],next[M],to[M],b[M];
 7 int read(){
 8     int sum=0;
 9     char ch=getchar();
10     while (ch<'0'||ch>'9')
11         ch=getchar();
12     while (ch>='0'&&ch<='9'){
13         sum=sum*10+ch-'0';
14         ch=getchar();
15     }
16     return sum;
17 }
18 void uni(int x,int y,int d){
19     size++;
20     next[size]=head[x];
21     head[x]=size;
22     to[size]=y;
23     b[size]=d;
24 }
25 int spfa(int mo){
26     for (int i=1;i<=n;i++){
27         vis[i]=0;
28         sum[i]=tmp;
29     }
30     int l=0,r=1;
31     que[1]=1;
32     vis[1]=1;
33     sum[1]=0;
34     while (l<=r){
35         l=(l+1)%10000;
36         int x=que[l];
37         vis[x]=0;
38         for (int e=head[x];e;e=next[e]){
39             int y=to[e];
40             if (w[y]<=mo&&sum[x]+b[e]<sum[y]){
41                 sum[y]=sum[x]+b[e];
42                 if (!vis[y]){
43                     r=(r+1)%10000;
44                     que[r]=y;
45                     vis[y]=1;
46                 }
47             }
48         }
49     }
50     if (sum[n]<=hp&&sum[n]!=tmp)//*
51         return 1;
52     return 0;
53 }
54 int main(){
55     int x,y,c;
56     size=0;
57     n=read();
58     m=read();
59     hp=read();
60     for (int i=1;i<=n;i++){
61         w[i]=read();
62         if (tmp<w[i])
63             tmp=w[i];
64     }
65     for (int i=1;i<=m;i++){
66         x=read();
67         y=read();
68         c=read();
69         uni(x,y,c);
70         uni(y,x,c);
71     }
72     int l=0,r=tmp;
73     if (!spfa(r)){
74         printf("AFK");
75         return 0;
76     }
77     while (l<r){
78         int mid=(l+r)>>1;
79         if (spfa(mid))
80             r=mid;
81         else
82             l=mid+1;
83     }
84     printf("%d",l);
85     return 0;
86 }
STD

 

posted on 2016-10-31 13:56  Absolutezero  阅读(233)  评论(0编辑  收藏  举报