zoukankan      html  css  js  c++  java
  • hdu 1087 A Plug for UNIX 最大流

    题意:http://www.phpfans.net/article/htmls/201012/MzI1MDQw.html

      1、在一个会议室里有n种插座,每种插座一个;

      2、每个插座只能插一种以及一个电器(或者适配器);

      3、有m个电器,每个电器有一个插头需要插在相应一种插座上;

      4、不是所有电器都能在会议室找到相应插座;

      5、有k种适配器,每种适配器可以有无限多数量;

      6、每种适配器(a, b)可以把b类插座变为a类插座;

      7、问最后有多少个电器无法使用。

    分析:图片来源http://www.cnblogs.com/longdouhzt/archive/2011/09/03/2165860.html

      

    网上给出的很直观的建图方式。看着很舒心,但是要注意。每种适配器(a, b)可以把b类插座变为a类插座。

    在图中,B->X, X->A,X->D是可以的,但是没有反向边。

    这个不知道的话,一直错。我以为是自己哪里错掉了。还换了算法做。

    SAP: 0MS

      1 #include<iostream>
      2 #include<cstdio>
      3 #include<cstring>
      4 #include<string>
      5 #include<map>
      6 #include<algorithm>
      7 using namespace std;
      8 
      9 const int N=1010;
     10 const int M=2*N*N, INF=0x3f3f3f3f;
     11 struct node
     12 {
     13     int to,next,w;
     14 }edge[M];
     15 int head[N],numh[N],h[N],cure[N],pre[N];
     16 int ans,tot;
     17 map<string,int> st;
     18 void SAP(int s, int e,int n)
     19 {
     20     int flow,u,tmp,neck,i;
     21     ans=0;
     22     for(i=1;i<=n;i++)
     23         cure[i]=head[i];
     24     numh[0]=n;
     25     u=s;
     26     while(h[s]<n)
     27     {
     28         if(u==e)
     29         {
     30             flow =INF;
     31             for(i=s;i!=e;i=edge[cure[i]].to)
     32             {
     33                 if(flow>edge[cure[i]].w)
     34                 {
     35                     neck=i;
     36                     flow =edge[cure[i]].w;
     37                 }
     38             }
     39             for(i=s;i!=e;i=edge[cure[i]].to)
     40             {
     41                 tmp=cure[i];
     42                 edge[tmp].w-=flow;
     43                 edge[tmp^1].w+=flow;
     44             }
     45             ans+=flow;
     46             u=neck;
     47         }
     48         for(i=cure[u];i!=-1;i=edge[i].next)
     49             if(edge[i].w && h[u]==h[edge[i].to]+1) break;
     50         if(i!=-1) {cure[u]=i;pre[edge[i].to]=u;u=edge[i].to;}
     51         else
     52         {
     53             if(0==--numh[h[u]]) break;
     54             cure[u]=head[u];
     55             for(tmp=n,i=head[u];i!=-1;i=edge[i].next)
     56                 if(edge[i].w) tmp=min(tmp, h[edge[i].to]);
     57             h[u]=tmp+1;
     58             ++numh[h[u]];
     59             if(u!=s) u=pre[u];
     60         }
     61     }
     62 }
     63 void init()
     64 {
     65     tot=0;
     66     memset(head,-1,sizeof(head));
     67     memset(pre,-1,sizeof(pre));
     68     memset(h,0,sizeof(h));
     69     memset(numh,0,sizeof(numh));
     70     st.clear();
     71 
     72 }
     73 void addedge(int i,int j,int w)
     74 {
     75     edge[tot].to=j;edge[tot].w=w;edge[tot].next=head[i];head[i]=tot++;
     76     edge[tot].to=i;edge[tot].w=0;edge[tot].next=head[j];head[j]=tot++;
     77 }
     78 char str[30],ch[30];
     79 int main()
     80 {
     81     //freopen("test.txt","r",stdin);
     82     int s,e,i,j,k,a,b,c,t;
     83     init();
     84     s=1;e=2;t=2;
     85     scanf("%d",&a);
     86     for(i=1;i<=a;i++){
     87         scanf("%s",str);
     88         if(st[str]==0)  st[str]=++t;
     89         addedge(st[str],e,1);
     90     }
     91     scanf("%d",&b);
     92     for(i=1;i<=b;i++){
     93         scanf("%s%s",ch,str);
     94         if(st[ch]==0) st[ch]=++t;
     95         if(st[str]==0) st[str]=++t;
     96         addedge(st[ch],st[str],1);
     97         addedge(s,st[ch],1);
     98     }
     99     scanf("%d",&c);
    100     for(i=1;i<=c;i++){
    101         scanf("%s%s",ch,str);
    102         if(st[ch]==0) st[ch]=++t;
    103         if(st[str]==0) st[str]=++t;
    104         addedge(st[ch],st[str],INF);
    105         //addedge(st[str],st[ch],INF);
    106     }
    107     SAP(s,e,t);
    108     printf("%d
    ",b-ans);
    109     return 0;
    110 }
    View Code

    EK: 32MS

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<cstring>
     4 #include<string>
     5 #include<map>
     6 #include<queue>
     7 #include<algorithm>
     8 using namespace std;
     9 map<string,int> st;
    10 const int N=510, INF=0x3f3f3f3f;
    11 int Map[N][N],pre[N],n,ans;
    12 bool vis[N];
    13 queue<int> que;
    14 bool EK_bfs(int s,int e)
    15 {
    16     int i,k;
    17     while(!que.empty()) que.pop();
    18     memset(vis,0,sizeof(vis));
    19     memset(pre,-1,sizeof(pre));
    20     que.push(s);
    21     vis[s]=1;
    22     while(!que.empty())
    23     {
    24         k=que.front();
    25         if(e==k)  return 1;
    26         que.pop();
    27         for(i=1;i<=n;i++)
    28         {
    29             if(Map[k][i]&&!vis[i])
    30             {
    31                 vis[i]=1;
    32                 pre[i]=k;
    33                 que.push(i);
    34             }
    35         }
    36     }
    37     return 0;
    38 }
    39 void EK(int s,int e)
    40 {
    41     int u,mn;
    42     ans=0;
    43     while(EK_bfs(s,e))
    44     {
    45         mn=INF;
    46         u=e;
    47         while(pre[u]!=-1)
    48         {
    49             mn=min(mn,Map[pre[u]][u]);
    50             u=pre[u];
    51         }
    52         ans+=mn;
    53         u=e;
    54         while(pre[u]!=-1)
    55         {
    56             Map[pre[u]][u]-=mn;
    57             Map[u][pre[u]]+=mn;
    58             u=pre[u];
    59         }
    60     }
    61 }
    62 void init()
    63 {
    64     memset(Map,0,sizeof(Map));
    65 }
    66 char str[30],ch[30];
    67 int main()
    68 {
    69     //freopen("test.txt","r",stdin);
    70     int s,e,i,j,k,a,b,c,t;
    71     init();
    72     s=1;e=2;t=2;
    73     scanf("%d",&a);
    74     for(i=1;i<=a;i++){
    75         scanf("%s",str);
    76         if(st[str]==0)  st[str]=++t;
    77         Map[st[str]][e]=1;
    78     }
    79     scanf("%d",&b);
    80     for(i=1;i<=b;i++){
    81         scanf("%s%s",ch,str);
    82         if(st[ch]==0) st[ch]=++t;
    83         if(st[str]==0) st[str]=++t;
    84         Map[st[ch]][st[str]]=1;
    85         Map[s][st[ch]]=1;
    86     }
    87     scanf("%d",&c);
    88     for(i=1;i<=c;i++){
    89         scanf("%s%s",ch,str);
    90         if(st[ch]==0) st[ch]=++t;
    91         if(st[str]==0) st[str]=++t;
    92         Map[st[ch]][st[str]]=INF;
    93         //Map[st[str]][st[ch]]=INF;
    94     }
    95     n=t;
    96     EK(s,e);
    97     printf("%d
    ",b-ans);
    98     return 0;
    99 }
    View Code
  • 相关阅读:
    JS,JQ及时监听input值的变化,MUI的input搜索框里的清除按钮的点击监听事件
    MUI 底部弹出的选择框
    MUI 拍照或选取照片上传作为头像
    多行文本文本输入框 textarea 可点击任意地方编辑的问题
    mui dtpicker 时间的设置 以及MUI的弹窗
    MUI 样式按钮的禁用
    利用渐变实现书本的效果
    调用sqlserver中的存储过程
    XmlHelper
    面试题 数据库sql
  • 原文地址:https://www.cnblogs.com/Potato-lover/p/3996378.html
Copyright © 2011-2022 走看看