• bzoj 4519: [Cqoi2016]不同的最小割 最小割树


    怎么求一张无向图中任意两点之间的最小割?

    http://fanhq666.blog.163.com/blog/static/8194342620113495335724/

    一张无向图不同的最小割最多有n-1个。

    所以可以用这些最小割建出一棵最小割树。

      1 #include<iostream>
      2 #include<cstring>
      3 #include<cstdio>
      4 #include<algorithm>
      5 #include<queue>
      6 #define inf 0x3f3f3f3f
      7 #define N 855
      8 #define M 400005
      9 using namespace std;
     10 int read()
     11 {
     12     int p=0;char c=getchar();
     13     while(c<'0'||c>'9')c=getchar();
     14     while(c>='0'&&c<='9')p=p*10+c-'0',c=getchar();
     15     return p;
     16 }
     17 int head[N],ver[M],nxt[M],f[M],tot,ch[N];
     18 void add(int a,int b,int c)
     19 {
     20     tot++;nxt[tot]=head[a];head[a]=tot;ver[tot]=b;f[tot]=c;return ;
     21 }
     22 queue<int>q;int S,T;
     23 bool tell()
     24 {
     25     memset(ch,-1,sizeof(ch));
     26     q.push(S);ch[S]=0;
     27     while(!q.empty())
     28     {
     29         int tmp=q.front();q.pop();
     30         for(int i=head[tmp];i;i=nxt[i])
     31         {
     32             if(f[i]&&ch[ver[i]]==-1)
     33             {
     34                 ch[ver[i]]=ch[tmp]+1;
     35                 q.push(ver[i]);
     36             }
     37         }
     38     }
     39     return ch[T]!=-1;
     40 }
     41 int zeng(int a,int b)
     42 {
     43     if(a==T)return b;
     44     int r=0;
     45     for(int i=head[a];i&&b>r;i=nxt[i])
     46     {
     47         if(f[i]&&ch[ver[i]]==ch[a]+1)
     48         {
     49             int t=zeng(ver[i],min(f[i],b-r));
     50             f[i]-=t;f[i^1]+=t;r+=t;
     51         }
     52     }
     53     if(!r)ch[a]=-1;
     54     return r;
     55 }
     56 int dinic()
     57 {
     58     int r=0,t;
     59     while(tell())while(t=zeng(S,inf))r+=t;
     60     return r;
     61 }
     62 void hui()
     63 {
     64     for(int i=2;i<=tot;i+=2)
     65     {
     66         f[i]=f[i^1]=(f[i]+f[i^1])>>1;
     67     }return ;
     68 }
     69 int tim;
     70 int c[N];
     71 void dfs(int x)
     72 {
     73     c[x]=tim;
     74     for(int i=head[x];i;i=nxt[i])
     75     {
     76         if(f[i]&&c[ver[i]]!=tim)dfs(ver[i]);
     77     }
     78     return ;
     79 }
     80 int p[N];
     81 int ans[N],cnt;
     82 int n,m;
     83 int st[N],st2[N];
     84 void solve(int l,int r)
     85 {
     86     if(l==r)return ;
     87     hui();
     88     S=p[l];T=p[r];
     89     int tmp=dinic();
     90     tim++;dfs(S);
     91     ans[++cnt]=tmp;
     92     int top1=0,top2=0;
     93     for(int i=l;i<=r;i++)
     94     {
     95         if(c[p[i]]==tim)st[++top1]=p[i];
     96         else st2[++top2]=p[i];
     97     }
     98     for(int i=l;i<=l+top1-1;i++)p[i]=st[i-l+1];
     99     for(int i=l+top1;i<=r;i++)p[i]=st2[i-l-top1+1];
    100     solve(l,l+top1-1);solve(l+top1,r);
    101 }
    102 int main()
    103 {
    104     scanf("%d%d",&n,&m);
    105     int t1,t2,t3;tot=1;
    106     for(int i=1;i<=m;i++)
    107     {
    108         t1=read();t2=read();t3=read();
    109         add(t1,t2,t3);add(t2,t1,t3);
    110     }
    111     for(int i=1;i<=n;i++)p[i]=i;
    112     solve(1,n);
    113     sort(ans+1,ans+cnt+1);
    114     int as=0;
    115     for(int i=1;i<=cnt;i++)
    116     {
    117         if(i==1||ans[i]!=ans[i-1])
    118         {
    119             as++;
    120         }
    121     }
    122     printf("%d
    ",as);
    123 }

                        

  • 相关阅读:
    Oracle学习笔记<5>
    Oracle学习笔记<4>
    fabric动态获取远程目录列表
    fabric查看本地与远程主机信息
    fabric安装使用
    pexpect实现远程操作
    pexpect的pxssh类实现远程操作
    Most Distant Point from the Sea
    Art Gallery
    Rotating Scoreboard(半平面交模板题)
  • 原文地址:https://www.cnblogs.com/ezyzy/p/6635827.html
Copyright © 2020-2023  润新知