hdu 2063

//Accepted 2063 0MS 284K 2225 B C++ 
#include<iostream>
#include<cstdio>
#include<queue>
#include<string>
using namespace std;
struct Edge{
 int u,v,c;
 int next;
}edg[5010];
int m,n,k,src,endp,e;
int dis[1010],stack[1010],head[1010],temp[1010];
inline void addedge(int u,int v,int c)
{
 edg[e].u = u; edg[e].v = v; edg[e].c = c;
 edg[e].next = head[u];
 head[u] = e++;
}
int bfs()
{
 queue<int>q;
 memset(dis,-1,sizeof(dis));
 q.push(src);
 int i,v,now,c;
 dis[src] = 0;
 while(!q.empty())
 {
  now = q.front();
  q.pop();
  for(i = head[now];i != -1;i = edg[i].next)
  {
   v = edg[i].v;
   c = edg[i].c;
   if(dis[v] == -1 && c > 0)
   {
    dis[v] = dis[now] + 1;
    q.push(v);
   }
  }
 }
 return (dis[endp] >= 0);
}
int dinic_dfs()
{
 int min,top,u,i,res,t,c,v;
 u = src;top = 0;res = 0;
 memcpy(temp,head,sizeof(temp));   //初始化temp 当前弧优化后的静态零接表弧头元素用辅助数组temp[]来保存
 while(1)
 {
  if(u == endp)
  {
   t = INT_MAX;min = -1;
   for(i = 0; i < top; i++)
   {
    if(edg[stack[i]].c < t)
    {
     t = edg[stack[i]].c;
     min = i;
    }
   }
   for(i = 0; i < top; i++)
   {
    v = stack[i];
    edg[v].c -= t;
    edg[v^1].c += t;
   }
   res += t;
   top = min;
   u = edg[stack[top]].u;
  }
  for(i = temp[u]; i != -1; i = edg[i].next)
  {
   v = edg[i].v;
   c = edg[i].c;
   if(dis[v] == dis[u] + 1 && c > 0)
   {
    break;
   }
  }
  if(i != -1)
  {
   stack[top++] = i;
   temp[u] = i;     //当前弧优化
   u = edg[i].v; 
  }
  else
  {
   if(top <= 0)break;
   top--;
   dis[u] = -1;
   u = edg[stack[top]].u;
  }
 }
 return res;
}
int dinic()
{
 int ans = 0,t;
 while(bfs())
 {
  t = dinic_dfs();
  if(t)
  ans += t;
 }
 return ans;
}
void solve()
{
 int i,s,t;
 while(scanf("%d",&k) != EOF && k)
 {
  scanf("%d %d",&m,&n);
  memset(head,-1,sizeof(head));
  e = 0;src = 0;endp = m + n + 1;
  for(i = 1; i <= m; i++ )
  {
   addedge(0,i,1);
   addedge(i,0,0);
     
  }
  for(i = 1; i <= n; i++)
  {
   addedge(i + m,endp,1);
   addedge(endp,i + m,0); 
  }
  for(i = 1; i <= k; i++)
  {
   scanf("%d %d",&s,&t);
   addedge(s,t + m,1);
   addedge(t + m,s,0);
  }
  printf("%d/n",dinic());
 }
}
int main()
{
 solve();
 return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值