• 八中生成树2 【最小生成树】


    本人水平有限,题解不到为处,请多多谅解

     

    本蒟蒻谢谢大家观看

    参考博客传送门 

    题目:

    1639: 八中生成树2

    Time Limit: 3 Sec  Memory Limit: 128 MB
    Submit: 170  Solved: 78
    [Submit][Status][Web Board]

    Description

    八中里面有N个建设物,M条边。
    对于这种要建最小生成树的问题,你应该很熟练了。
    现在老大决定降低某条边的费用,然后这条边必须要被选中,因为这条路他每天都要走,自然......
    问选了这条边后是否可以得到一个比从前总开支相等或更小的方案。

    Input

    第一行三个整数N,M,Q(1<=N<=1000,N-1<=M<=100000
    接下来M行,每行三个整数(X,Y,Z)描述一条可以建造的路。 0<=Z<=10000 
    最后Q行,每行两个整数i,x(1<=i<=M,0<=x)描述一个修改计划,
    即要你判断如果 将第i条公路的修建费用降低为x元后,是否可以得到一个比从前总开支相等或更小的方案

    Output

    按顺序输出Q行,每行输出"Yes"或"No",Yes表示可以建造,No表示不可能

    Sample Input

    3 4 3
    1 2 10
    1 3 6
    2 3 4
    1 3 7
    4 6
    1 7
    1 5

    Sample Output

    Yes
    No
    Yes

    HINT

    我们先可以用prim算法构造最小生成树,因为题目要求必须走它给的边,我们就可以也把这条边存储,然后由这一个点延伸。当我们求出这一条边所对应的点的最大值,与它所给的降价比较,若比其还小,则肯定为NO

    code:

     1 #include<bits/stdc++.h>
     2 #define max(a,b) ((a)>(b)?(a):(b))
     3 #define min(a,b) ((a)<(b)?(a):(b))
     4 const int N=1e5+10;
     5 const int INF=0x3f3f3f3f;
     6 int n,m,k;
     7 int f[1011][1011],mx[1011][1011];
     8 int pre[N],dis[N],flag[N];
     9 int e=1;
    10 void inint(){
    11     freopen("tree.in","r",stdin);
    12     freopen("tree.out","w",stdout);
    13 }
    14 inline int read(){
    15     int x=0,f=1;char ch=getchar();
    16     while(!isdigit(ch)){if(ch=='-')f=-1;ch=getchar();}
    17     while(isdigit(ch)){x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}
    18     return x*f;
    19 }
    20 struct oo{
    21     int u,v,w;
    22 } a[N*100];
    23 void prim(){
    24     memset(flag,0,sizeof(flag));
    25     int now=1;
    26     for(int i=1; i<=n; i++){
    27         dis[i]=f[1][i];
    28     }
    29     dis[1]=0;
    30     flag[1]=1;
    31     pre[1]=1;
    32     for(int i=1; i<=n; i++) {
    33         int minn=INF;
    34         for(int j=1; j<=n; j++){
    35             if(!flag[j]&&dis[j]<minn){
    36                 minn=dis[j];
    37                 now=j;
    38             }
    39         }
    40         for(int j=1; j<=n; j++){
    41             if(flag[j]){
    42                 mx[now][j]=max(mx[j][pre[now]],dis[now]);
    43                 mx[j][now]=mx[now][j];
    44             }
    45         }
    46         flag[now]=1;
    47         for(int j=1; j<=n; j++){
    48             if(!flag[j]&&dis[j]>f[now][j]){
    49                 dis[j]=f[now][j];
    50                 pre[j]=now;
    51             }
    52         }
    53     }
    54     return ;
    55 }
    56 int main()
    57 {
    58     //inint();
    59     n=read(),m=read(),k=read();
    60     memset(f,63,sizeof(f));
    61     memset(mx,0,sizeof(mx));
    62     for(int i=1; i<=n; i++){
    63         f[i][i]=0;
    64     }
    65     for(int i=1,u,v,w;i<=m;i++){
    66         u=read(),v=read(),w=read();
    67         a[e].u=u;
    68         a[e].v=v;
    69         a[e].w=w;
    70         e++;
    71         f[u][v]=f[v][u]=min(f[u][v],w);
    72     }
    73     prim();
    74     int num,c;
    75     while(k--){
    76         num=read(),c=read();
    77         if(mx[a[num].u][a[num].v]>=c){
    78             printf("Yes
    ");
    79         }
    80         else{
    81             printf("No
    ");
    82         }
    83     }
    84     return 0;
    85 }
    86 /*
    87 3 4 3
    88 1 2 10
    89 1 3 6
    90 2 3 4
    91 1 3 7
    92 4 6
    93 1 7
    94 1 5
    95 */
  • 相关阅读:
    eclipse运行maven项目报错:找不到ContextLoaderListener、IntrospectorCleanupListener
    音乐播放器项目计划进度安排
    音乐播放器计划书
    抽奖程序
    显示默认目录中的所有文件名
    单字符和多字符的文件输出
    求和
    第二周 登录小界面
    第一周随笔
    小组图书管理系统项目进度表
  • 原文地址:https://www.cnblogs.com/nlyzl/p/11776228.html
Copyright © 2020-2023  润新知