• poj 3308(最小点权覆盖、最小割)


    题目链接:http://poj.org/problem?id=3308

    思路:裸的最小点权覆盖,建立超级源点和超级汇点,将源点与行相连,容量为这行消灭敌人的代价,将列与汇点相连,容量为这列消灭敌人的代价,对于每一个敌人(x,y),连边x->y,容量为inf,这样就说明选取的点覆盖了那些边(敌人),然后跑最大流求最小割即可。

    PS:这里是乘积最小,要取对数转化为和最小。

      1 #include<iostream>
      2 #include<cstdio>
      3 #include<cstring>
      4 #include<algorithm>
      5 #include<queue>
      6 #include<cmath>
      7 using namespace std;
      8 #define MAXN 222
      9 #define MAXM 444444
     10 #define inf 1<<30
     11 
     12 struct Edge{
     13     int v,next;
     14     double cap;
     15 }edge[MAXM];
     16 
     17 int n,m,T,NE,NV,vs,vt;
     18 int head[MAXN];
     19 
     20 void Insert(int u,int v,double cap)
     21 {
     22     edge[NE].v=v;
     23     edge[NE].cap=cap;
     24     edge[NE].next=head[u];
     25     head[u]=NE++;
     26 
     27     edge[NE].v=u;
     28     edge[NE].cap=0;
     29     edge[NE].next=head[v];
     30     head[v]=NE++;
     31 }
     32 
     33 int level[MAXN],gap[MAXN];
     34 void bfs(int vt)
     35 {
     36     memset(level,-1,sizeof(level));
     37     memset(gap,0,sizeof(gap));
     38     level[vt]=0;
     39     gap[level[vt]]++;
     40     queue<int>que;
     41     que.push(vt);
     42     while(!que.empty()){
     43         int u=que.front();
     44         que.pop();
     45         for(int i=head[u];i!=-1;i=edge[i].next){
     46             int v=edge[i].v;
     47             if(level[v]<0){
     48                 level[v]=level[u]+1;
     49                 gap[level[v]]++;
     50                 que.push(v);
     51             }
     52         }
     53     }
     54 }
     55 
     56 int pre[MAXN],cur[MAXN];
     57 double SAP(int vs,int vt)
     58 {
     59     bfs(vt);
     60     memset(pre,-1,sizeof(pre));
     61     memcpy(cur,head,sizeof(head));
     62     double maxflow=0,aug=inf;
     63     int u=pre[vs]=vs;
     64     gap[0]=NV;
     65     while(level[vs]<NV){
     66         bool flag=false;
     67         for(int &i=cur[u];i!=-1;i=edge[i].next){
     68             int v=edge[i].v;
     69             if(edge[i].cap>0&&level[u]==level[v]+1){
     70                 flag=true;
     71                 pre[v]=u;
     72                 u=v;
     73                 aug=min(aug,edge[i].cap);
     74                 if(v==vt){
     75                     maxflow+=aug;
     76                     for(u=pre[v];v!=vs;v=u,u=pre[u]){
     77                         edge[cur[u]].cap-=aug;
     78                         edge[cur[u]^1].cap+=aug;
     79                     }
     80                     aug=inf;
     81                 }
     82                 break;
     83             }
     84         }
     85         if(flag)continue;
     86         int minlevel=NV;
     87         for(int i=head[u];i!=-1;i=edge[i].next){
     88             int v=edge[i].v;
     89             if(edge[i].cap>0&&level[v]<minlevel){
     90                 minlevel=level[v];
     91                 cur[u]=i;
     92             }
     93         }
     94         if(--gap[level[u]]==0)break;
     95         level[u]=minlevel+1;
     96         gap[level[u]]++;
     97         u=pre[u];
     98     }
     99     return maxflow;
    100 }
    101 
    102 int main()
    103 {
    104     double x,y;
    105     int _case,u,v;
    106     scanf("%d",&_case);
    107     while(_case--){
    108         scanf("%d%d%d",&n,&m,&T);
    109         NE=0;
    110         memset(head,-1,sizeof(head));
    111         vs=0,vt=n+m+1,NV=vt+1;
    112         for(int i=1;i<=n;i++){
    113             scanf("%lf",&x);
    114             Insert(vs,i,log(x));
    115         }
    116         for(int i=1;i<=m;i++){
    117             scanf("%lf",&y);
    118             Insert(i+n,vt,log(y));
    119         }
    120         while(T--){
    121             scanf("%d%d",&u,&v);
    122             Insert(u,v+n,inf);
    123         }
    124         double ans=SAP(vs,vt);
    125         printf("%.4f
    ",exp(ans));
    126     }
    127     return 0;
    128 }
    View Code
  • 相关阅读:
    SQL中的字符串字段根据某字段实现自增
    SQL中的字符串字段实现自增
    ECS Windows服务器IIS FTP登陆提示“530 valid hostname is expected”
    HTML中动态生成内容的事件绑定问题
    JavaScript对JSON数据进行排序和搜索
    IIS站点下多应用程序 C#获取根目录方法
    asp.net中form表单多个按钮submit提交到后台的实例
    C#从一个SqlCommand对象生成可执行的SQL语句
    传递参数
    js创建jsonArray传输至后台及后台解析
  • 原文地址:https://www.cnblogs.com/wally/p/3280542.html
Copyright © 2020-2023  润新知