• bzoj1711: [Usaco2007 Open]Dining吃饭


    建图后跑最大流即可

    #include<cstdio>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    using namespace std;
    #define rep(i,n) for(int i=1;i<=n;i++)
    #define clr(x,c) memset(x,c,sizeof(x))
    #define qwq(x) for(edge *o=head[x];o;o=o->next)
    const int nmax=505;
    const int maxn=40005;
    const int inf=0x7f7f7f7f;
    int read(){
    	int x=0;char c=getchar();bool f=true;
    	while(!isdigit(c)){
    		if(c=='-') f=false;c=getchar();
    	}
    	while(isdigit(c)) x=x*10+c-'0',c=getchar();
    	return f?x:-x;
    }
    struct edge{
    	int to,cap;edge *next,*rev;
    };
    edge edges[maxn],*pt,*head[nmax],*cur[nmax],*p[nmax];
    void add(int u,int v,int w){
    	pt->to=v;pt->cap=w;pt->next=head[u];head[u]=pt++;
    }
    void adde(int u,int v,int w){
    	add(u,v,w);add(v,u,0);head[u]->rev=head[v];head[v]->rev=head[u];
    }
    int cnt[nmax],h[nmax];
    int maxflow(int s,int t,int n){
    	clr(cnt,0);cnt[0]=n;clr(h,0);
    	int flow=0,a=inf,x=s;edge *e;
    	while(h[s]<n){
    		for(e=cur[x];e;e=e->next) if(e->cap>0&&h[x]==h[e->to]+1) break;
    		if(e){
    			p[e->to]=cur[x]=e;a=min(a,e->cap);x=e->to;
    			if(x==t){
    				while(x!=s) p[x]->cap-=a,p[x]->rev->cap+=a,x=p[x]->rev->to;
    				flow+=a,a=inf;
    			}
    		}else{
    			if(!--cnt[h[x]]) break;
    			h[x]=n;
    			for(e=head[x];e;e=e->next) if(e->cap>0&&h[x]>h[e->to]+1) cur[x]=e,h[x]=h[e->to]+1;
    			cnt[h[x]]++;
    			if(x!=s) x=p[x]->rev->to;
    		}
    	}
    	return flow;
    }
    int main(){
    	pt=edges;clr(head,0);
    	int n=read(),F=read(),D=read(),u,v,s=0,t=F+D+n+n+1;
    	rep(i,n){
    		adde(F+i,F+n+i,1);
    		u=read(),v=read();
    		rep(j,u) adde(read(),F+i,1);
    		rep(j,v) adde(F+n+i,F+n+n+read(),1);
    	}
    	rep(i,F) adde(s,i,1);
    	rep(i,D) adde(F+n+n+i,t,1);
    	printf("%d
    ",maxflow(s,t,t+1));
    	return 0;
    }
    

     

    1711: [Usaco2007 Open]Dining吃饭

    Time Limit: 5 Sec  Memory Limit: 64 MB
    Submit: 815  Solved: 422
    [Submit][Status][Discuss]

    Description

    农夫JOHN为牛们做了很好的食品,但是牛吃饭很挑食. 每一头牛只喜欢吃一些食品和饮料而别的一概不吃.虽然他不一定能把所有牛喂饱,他还是想让尽可能多的牛吃到他们喜欢的食品和饮料. 农夫JOHN做了F (1 <= F <= 100) 种食品并准备了D (1 <= D <= 100) 种饮料. 他的N (1 <= N <= 100)头牛都以决定了是否愿意吃某种食物和喝某种饮料. 农夫JOHN想给每一头牛一种食品和一种饮料,使得尽可能多的牛得到喜欢的食物和饮料. 每一件食物和饮料只能由一头牛来用. 例如如果食物2被一头牛吃掉了,没有别的牛能吃食物2.

    Input

    * 第一行: 三个数: N, F, 和 D

    * 第2..N+1行: 每一行由两个数开始F_i 和 D_i, 分别是第i 头牛可以吃的食品数和可以喝的饮料数.下F_i个整数是第i头牛可以吃的食品号,再下面的D_i个整数是第i头牛可以喝的饮料号码.

    Output

    * 第一行: 一个整数,最多可以喂饱的牛数.

    Sample Input

    4 3 3
    2 2 1 2 3 1
    2 2 2 3 1 2
    2 2 1 3 1 2
    2 1 1 3 3

    输入解释:

    牛 1: 食品从 {1,2}, 饮料从 {1,2} 中选
    牛 2: 食品从 {2,3}, 饮料从 {1,2} 中选
    牛 3: 食品从 {1,3}, 饮料从 {1,2} 中选
    牛 4: 食品从 {1,3}, 饮料从 {3} 中选

    Sample Output

    3
    输出解释:

    一个方案是:
    Cow 1: 不吃
    Cow 2: 食品 #2, 饮料 #2
    Cow 3: 食品 #1, 饮料 #1
    Cow 4: 食品 #3, 饮料 #3
    用鸽笼定理可以推出没有更好的解 (一共只有3总食品和饮料).当然,别的数据会更难.

    HINT

     

    Source

    [Submit][Status][Discuss]
  • 相关阅读:
    java动态编译 (java在线执行代码后端实现原理)(二)
    java动态编译 (java在线执行代码后端实现原理)
    自己根据java的LinkedList源码编写的一个简单的LinkedList实现
    postman中 form-data、x-www-form-urlencoded、raw、binary的区别
    什么是Base64加密?为什么要有Base64加密?
    js获取上个月的第一天和最后一天
    js一个数组变为指定长度的多个数组
    java人民币转大写中文
    三天打鱼两天晒网
    一句便是一首【一】
  • 原文地址:https://www.cnblogs.com/fighting-to-the-end/p/5658545.html
Copyright © 2020-2023  润新知