• POJ 2987 Firing 网络流 最大权闭合图


    http://poj.org/problem?id=2987

    https://blog.csdn.net/u014686462/article/details/48533253

    给一个闭合图,要求输出其最大权闭合图的权值和需要选的最少点数,最大权闭合图定义和网络流连边方式见博客。

     1 #include<cstdio>
     2 #include<cstring>
     3 #include<algorithm>
     4 #include<cmath>
     5 #include<iostream>
     6 #include<queue>
     7 using namespace std;
     8 #define LL long long
     9 const int maxn=10010;
    10 const LL minf=(LL)1e14;
    11 int n,m,s,t;
    12 LL val[maxn]={};
    13 struct nod{
    14     int y,next;LL v;
    15 }e[maxn*20];
    16 int head[maxn],tot=1;
    17 queue<int>q;
    18 int dep[maxn]={},vis[maxn]={},id[maxn]={},tai=0;
    19 void init(int x,int y,LL v){
    20     e[++tot].y=y;e[tot].v=v;e[tot].next=head[x];head[x]=tot;
    21 }
    22 bool dfs(){
    23     memset(dep,0,sizeof(dep));
    24     q.push(s);dep[s]=1;
    25     while(!q.empty()){
    26         int x=q.front();q.pop();
    27         for(int i=head[x];i;i=e[i].next){
    28             if(e[i].v&&!dep[e[i].y]){
    29                 dep[e[i].y]=dep[x]+1;
    30                 q.push(e[i].y);
    31             }
    32         }
    33     }
    34     return dep[t];
    35 }
    36 LL dfs1(int x,LL fc){
    37     if(x==t){
    38         return fc;
    39     }
    40     LL he=0,z;
    41     for(int i=head[x];i;i=e[i].next){
    42         if(dep[x]+1==dep[e[i].y]){
    43             z=dfs1(e[i].y,min(fc-he,e[i].v));
    44             he+=z;e[i].v-=z;e[i^1].v+=z;
    45             if(he==fc)break;
    46         }
    47     }
    48     return he;
    49 }
    50 void dfs2(int x){
    51     if(x==t)return;
    52     if(x!=s)id[++tai]=x;
    53     vis[x]=1;
    54     for(int i=head[x];i;i=e[i].next){
    55         if(e[i].v&&!vis[e[i].y]){
    56             dfs2(e[i].y);
    57         }
    58     }
    59 }
    60 int main(){
    61     int x,y; LL ans=0;
    62     scanf("%d%d",&n,&m);
    63     s=n+1;t=s+1;
    64     for(int i=1;i<=n;i++){
    65         scanf("%lld",&val[i]);
    66         if(val[i]>=0){init(s,i,val[i]);init(i,s,0);ans=ans+val[i];}
    67         else {init(i,t,-val[i]);init(t,i,0);}
    68     }
    69     for(int i=1;i<=m;i++){
    70         scanf("%d%d",&x,&y);
    71         init(x,y,minf);init(y,x,0);
    72     }
    73     while(dfs())ans-=dfs1(s,minf);
    74     dfs2(s);
    75     printf("%d ",tai);
    76     printf("%lld
    ",ans);
    77     return 0;
    78 }
    View Code

  • 相关阅读:
    python 冒泡排序
    python链式调用REST API把参数放到URL中
    python assert断言用法
    python实现斐波那契数列
    Pycharm快捷键集合
    linux shell中$0,$?,$!等的特殊用法
    搭建邮箱服务器
    linux安装IB驱动方法
    Oracle:Redhat 7.4+Oracle Rac 11.2.0.4 执行root.sh报错处理
    Struts学习(一)
  • 原文地址:https://www.cnblogs.com/137shoebills/p/9100790.html
Copyright © 2020-2023  润新知