P1396 营救 图方面的二分

题意:给出一个n个点,m条边的图,每条边有一个拥挤度

   让我们从s走到t,使最大的拥挤度最小

思路:每一次遍历图的复杂度为n,二分遍历的复杂度即为(n*logn)

   我们定一个L R的边界

      然后check,每一次check便是一次遍历,每次遍历假如能够在某个拥挤度之下走到终点,则满足,反之不满足

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 const int maxn=5e4+10;
 4 int s,t;
 5 struct node
 6 {
 7     int v,w;
 8     int nxt;
 9 }G[maxn]; int head[maxn]; int num;
10 int flag;
11 void add(int u,int v,int w)
12 {
13     G[++num].v=v;G[num].w=w;G[num].nxt=head[u];head[u]=num;
14 }
15 void dfs(int u,int fa,int limit)
16 {
17     if(flag) return;
18     if(u==t){
19         flag=1;
20         return;
21     }
22     for(int i=head[u];i;i=G[i].nxt){
23         int v=G[i].v;int w=G[i].w;
24         if(v==fa) continue;
25         if(w>limit) continue;
26         dfs(v,u,limit);
27     }
28 }
29 int check(int mid)
30 {
31     flag=0;
32     dfs(s,0,mid);
33     if(flag) return 1;
34     else return 0;
35 }
36 int main()
37 {
38     int n,m;
39     scanf("%d%d%d%d",&n,&m,&s,&t);
40     for(int i=1;i<=m;i++){
41         int u,v,w;
42         scanf("%d%d%d",&u,&v,&w);
43         add(u,v,w);
44         add(v,u,w);
45     }
46     int L=1;int R=1e4;
47     int ans;
48     while(L<=R){
49        // printf("ans:%d\n",ans);
50         int mid=L+R>>1;
51         if(check(mid)){
52             ans=mid;
53             R=mid-1;
54         }
55         else{
56             L=mid+1;
57         }
58     }
59     printf("%d\n",ans);
60     return 0;
61 }
View Code

猜你喜欢

转载自www.cnblogs.com/pangbi/p/12681622.html