POJ-3821-Dining (拆点网络流)
这题为什么不能用 左边放食物,中间放牛,后面放水?
原因很简单,假设一头牛喜欢两个食物AB和两种水AB。
此时可以从一个食物A,走到牛A,再走到水A。
但是还可以有另一条路,从另一个食物B,走到该牛A,并走到该牛喜欢的另一个水B。
这是错误的原因之一,其实也跟反边有关。
所以对于牛,拆开,中间建立一条边,说明该牛已经使用过,这样也避免了从其它食物C走到牛A,此时我们希望它走反边,即牛A到食物A,再从食物A走向其它牛等等,但是却在到达牛A的时候,走向了水B的情况。
#include <iostream>
#include <stdio.h>
#include <queue>
#include <string.h>
using namespace std;
int n,f,d,fi,di;
const int INF=0x3f3f3f3f;
const int maxn=110;
struct Edge {
int to,cap,flow;
};
struct Dinic {
int s,t,cnt;
Edge edge[maxn*maxn*2];
int head[maxn*4];
int next[maxn*maxn*2];
int deep[maxn*4];
int cur[maxn*4];
bool vis[maxn*4];
void addEdge(int u,int v,int w)
{
edge[cnt].to=v;
edge[cnt].cap=w;
edge[cnt].flow=0;
next[cnt]=head[u];
head[u]=cnt++;
edge[cnt].to=u;
edge[cnt].flow=0;
edge[cnt].cap=0;
next[cnt]=head[v];
head[v]=cnt++;
}
void init()
{
s=0;
t=401;
cnt=0;
memset(head,-1,sizeof(head));
for (int i=1;i<=100;i++) {
addEdge(s,i,1);
}
for (int i=301;i<=400;i++) {
addEdge(i,t,1);
}
}
bool bfs()
{
memset(deep,0,sizeof(deep));
memset(vis,0,sizeof(vis));
queue<int> q;
vis[s]=true;
deep[s]=0;
q.push(s);
while (!q.empty()) {
int u=q.front();
q.pop();
for (int i=head[u];i!=-1;i=next[i]) {
Edge &e=edge[i];
if (!vis[e.to]&&e.cap>e.flow) {
deep[e.to]=deep[u]+1;
vis[e.to]=true;
q.push(e.to);
}
}
}
return vis[t];
}
int dfs(int u,int in)
{
if (u==t||in==0) {
return in;
}
int out=0,f=0;
for (int &i=cur[u];i!=-1;i=next[i]) {
Edge &e=edge[i];
if (deep[e.to]==deep[u]+1&&(f=dfs(e.to,min(e.cap-e.flow,in)))>0) {
in-=f;
out+=f;
edge[i].flow+=f;
edge[i^1].flow-=f;
if (in==0) {
break;
}
}
}
return out;
}
int maxflow()
{
int ans=0;
while (bfs()) {
for (int i=0;i<4*maxn;i++) {
cur[i]=head[i];
}
ans+=dfs(s,INF);
}
return ans;
}
void print()
{
for (int i=0;i<=400;i++) {
if (head[i]!=-1) {
printf("%d:",i);
for (int j=head[i];j!=-1;j=next[j]) {
printf("%d %d %d ",edge[j].to,edge[j].cap,edge[j].flow);
}
printf("\n");
}
}
}
}DC;
int main()
{
int food,drink;
scanf("%d%d%d",&n,&f,&d);
DC.init();
for (int i=1;i<=n;i++) {
scanf("%d%d",&fi,&di);
for (int j=0;j<fi;j++) {
scanf("%d",&food);
DC.addEdge(food,100+i,1);
}
DC.addEdge(100+i,200+i,1);
for (int j=0;j<di;j++) {
scanf("%d",&drink);
DC.addEdge(i+200,drink+300,1);
}
}
//DC.print();
printf("%d\n",DC.maxflow());
return 0;
}
/*
2 2 2
1 1 2 1
2 1 2 1 2
*/
POJ-3821-Dining (拆点网络流)的更多相关文章
- POJ 3281 Dining (拆点)【最大流】
<题目链接> 题目大意: 有N头牛,F种食物,D种饮料,每一头牛都有自己喜欢的食物和饮料,且每一种食物和饮料都只有一份,让你分配这些食物和饮料,问最多能使多少头牛同时获得自己喜欢的食物和饮 ...
- poj 3281 Dining 拆点 最大流
题目链接 题意 有\(N\)头牛,\(F\)个食物和\(D\)个饮料.每头牛都有自己偏好的食物和饮料列表. 问该如何分配食物和饮料,使得尽量多的牛能够既获得自己喜欢的食物又获得自己喜欢的饮料. 建图 ...
- poj 3281 Dining(网络流+拆点)
Dining Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 20052 Accepted: 8915 Descripti ...
- POJ 3281 Dining (网络流)
POJ 3281 Dining (网络流) Description Cows are such finicky eaters. Each cow has a preference for certai ...
- POJ 3281 Dining(最大流)
POJ 3281 Dining id=3281" target="_blank" style="">题目链接 题意:n个牛.每一个牛有一些喜欢的 ...
- POJ 2135 Farm Tour (网络流,最小费用最大流)
POJ 2135 Farm Tour (网络流,最小费用最大流) Description When FJ's friends visit him on the farm, he likes to sh ...
- POJ 2516 Minimum Cost (网络流,最小费用流)
POJ 2516 Minimum Cost (网络流,最小费用流) Description Dearboy, a goods victualer, now comes to a big problem ...
- POJ 3281 Dining(网络流拆点)
[题目链接] http://poj.org/problem?id=3281 [题目大意] 给出一些食物,一些饮料,每头牛只喜欢一些种类的食物和饮料, 但是每头牛最多只能得到一种饮料和食物,问可以最多满 ...
- POJ - 3281 Dining(拆点+最大网络流)
Dining Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 18230 Accepted: 8132 Descripti ...
- 图论--网络流--最大流--POJ 3281 Dining (超级源汇+限流建图+拆点建图)
Description Cows are such finicky eaters. Each cow has a preference for certain foods and drinks, an ...
随机推荐
- idea tomcat启动无效
今天换了台电脑,用idea 部署tomcat启动死活启动不了,报 Application Server was not connected before run configuration stop, ...
- 解决:配置虚拟主机,重启apache,[warn] _default_ VirtualHost overlap on port 80, the first has precedence
http://blog.csdn.net/kaizhu_qin/article/details/17506293 很多第一次配置apache的虚拟主机的时候,以为配置第一个虚拟主机完成以后,以后就不会 ...
- Hibernate知识点整理
一, Hibernate 介绍: Hibernate 只是一个将持久化类与数据库表相映射的工具,每个持久化类实例均对应于数据库表中的一个数据行而已.用户只需直接使用面向对象的方法操作此持久化类实例,即 ...
- 题解 P1453 【城市环路】
P1453 城市环路 感觉基环树(or环套树)的题目一般都是找到树上的环,断掉一条边再进行树上的操作(如noip2018P5022 旅行) 双倍经验:P2607 [ZJOI2008]骑士 P1453和 ...
- IntelliJ IDEA 2017.3尚硅谷-----设置自动编译
- 计算几何-LA2218-HPI-第一次卡精度-vijos1087-铁人三项
This article is made by Jason-Cow.Welcome to reprint.But please post the writer's address. http://ww ...
- configure: error: no acceptable C compiler found in $PATH 解决
在安装keepalived时报错 ./configure --prefix=/usr/local/ccbase/keepalived-2.0.15 && make && ...
- 吴裕雄 python 机器学习——多项式贝叶斯分类器MultinomialNB模型
import numpy as np import matplotlib.pyplot as plt from sklearn import datasets,naive_bayes from skl ...
- opencv静态编译
在Windows下opencv静态编译. 使用cmake生成visual Studio 2015 解决方案如下图所示: 重点看红色框线里的内容,先编译ALL_BUILD,这样就把所有子项目编译成功.所 ...
- Docker - Docker 镜像 简介
概述 简单介绍一下 docker 镜像的概念 1. 背景 复习 docker 镜像是 docker 最基础, 最重要的概念之一 所以正式使用之前, 最好有所理解和认识 2. 镜像 概述 简单描述 理解 ...