一种很普遍的做法就是把一个带有容量的点拆成两个点,一个入点一个出点,链接两个点的边的权值为这个点的容量

hdu3732

#include<cstdio>
#include<cstring>
#include<algorithm>
#include<queue>
#include<vector>
#include<string>
#include<iostream>
#define INF 1e9
using namespace std;
const int maxn =+; struct Edge
{
int from,to,cap,flow;
Edge(){}
Edge(int f,int t,int c,int fl):from(f),to(t),cap(c),flow(fl){}
}; struct Dinic
{
int n,m,s,t;
vector<Edge> edges;
vector<int> G[maxn];
int cur[maxn];
int d[maxn];
bool vis[maxn]; void init(int n,int s,int t)
{
this->n=n, this->s=s, this->t=t;
edges.clear();
for(int i=;i<n;i++) G[i].clear();
} void AddEdge(int from,int to,int cap)
{
edges.push_back( Edge(from,to,cap,) );
edges.push_back( Edge(to,from,,) );
m = edges.size();
G[from].push_back(m-);
G[to].push_back(m-);
} bool BFS()
{
queue<int> Q;
Q.push(s);
memset(vis,,sizeof(vis));
d[s]=;
vis[s]=true;
while(!Q.empty())
{
int x=Q.front(); Q.pop();
for(int i=;i<G[x].size();++i)
{
Edge& e=edges[G[x][i]];
if(!vis[e.to] && e.cap>e.flow)
{
d[e.to]=+d[x];
vis[e.to]=true;
Q.push(e.to);
}
}
}
return vis[t];
} int DFS(int x,int a)
{
if(x==t || a==) return a;
int flow=,f;
for(int& i=cur[x];i<G[x].size();++i)
{
Edge& e=edges[G[x][i]];
if(d[e.to]==d[x]+ && (f=DFS(e.to,min(a,e.cap-e.flow) ) )>)
{
e.flow +=f;
edges[G[x][i]^].flow -=f;
flow +=f;
a-=f;
if(a==) break;
}
}
return flow;
} int max_flow()
{
int ans=;
while(BFS())
{
memset(cur,,sizeof(cur));
ans += DFS(s,INF);
}
return ans;
}
}DC; int main()
{
int T; scanf("%d",&T);
for(int kase=;kase<=T;++kase)
{
int n,m,d,src,dst;
int sum=;//蜥蜴数
scanf("%d%d",&n,&d);
for(int i=;i<=n;i++)
{
string s;
cin>>s;
if(i==)//第一次
{
m = s.size();
src=, dst=*n*m+;
DC.init(*n*m+,src,dst);
}
for(int j=;j<s.size();++j)if(s[j]-''>)
{
int id = (i-)*m+j+;//当前点编号
DC.AddEdge(id, id+n*m, s[j]-'');
if(i<=d || i+d>n || j<d || j+d>=m)//当前格子能直接跳出棋盘
{
DC.AddEdge(id+n*m,dst,INF);
}
else //不能直接跳出去
{
for(int k=;k<=n;k++)
for(int h=;h<m;h++)
{
int id2= (k-)*m+h+;
if(id==id2) continue;
if(abs(i-k)+abs(j-h)<= d) DC.AddEdge(id+n*m,id2,INF);
}
}
}
}
for(int i=;i<=n;++i)
{
string s;
cin>>s;
for(int j=;j<s.size();++j)
{
int id = (i-)*m+j+;//当前点编号
if(s[j]=='L')
{
++sum;
DC.AddEdge(src,id,);
}
}
}
int ans = sum-DC.max_flow();
if(ans==) printf("Case #%d: no lizard was left behind.\n",kase);
else if(ans==) printf("Case #%d: 1 lizard was left behind.\n",kase);
else printf("Case #%d: %d lizards were left behind.\n",kase,ans);
}
return ;
}

poj3436

#include<cstdio>
#include<iostream>
#include<cstring>
#define Maxn 110
using namespace std; const int inf=0x3f3f3f3f;
struct line{
int to,next,cap;
}p[Maxn*Maxn*];
int head[Maxn];
int q[Maxn];
int d[Maxn];
int cur[Maxn];
int tot;
int src,t;
int n,m;
void addedge(int a,int b,int c){
p[tot].to=b;
p[tot].next=head[a];
p[tot].cap=c;
head[a]=tot++;
}
void insert(int a,int b,int c){
addedge(a,b,c);
addedge(b,a,);
}
bool bfs(){
memset(d,-,sizeof d);
int s=,e=-;
q[++e]=src;
d[src]=;
while(s<=e){
int u=q[s++];
for(int i=head[u];i!=-;i=p[i].next){
int v=p[i].to;
if(d[v]==-&&p[i].cap){
d[v]=d[u]+;
q[++e]=v;
}
}
}
return d[t]!=-;
}
int dfs(int u,int alpha){
if(u==t) return alpha;
int w,used=;
for(int i=cur[u];i!=-&&used<alpha;i=p[i].next){
int v=p[i].to;
if(p[i].cap&&d[v]==d[u]+){
w=dfs(v,min(alpha-used,p[i].cap));
used+=w;
p[i].cap-=w;
p[i^].cap+=w;
cur[u]=i;
}
}
if(!used) d[u]=-;
return used;
}
int dinic(){
int ans=;
src=,t=*m+;
while(bfs()){
for(int i=src;i<=t;i++) cur[i]=head[i];
ans+=dfs(src,inf);
}
return ans;
}
int num[Maxn];
int input[Maxn][],output[Maxn][];
int vis[Maxn][Maxn];
bool check(int x,int y){
return x==y||y==;
}
bool ck1(int d){ //没有1
for(int i=;i<n;i++)
if(input[d][i]==) return false;
return true;
}
bool ck2(int d){ //全1
for(int i=;i<n;i++)
if(output[d][i]!=) return false;
return true;
}
int main()
{
while(~scanf("%d%d",&n,&m)){
for(int i=;i<=m;i++){
scanf("%d",num+i);
for(int j=;j<n;j++)
scanf("%d",&input[i][j]);
for(int j=;j<n;j++)
scanf("%d",&output[i][j]);
}
memset(head,-,sizeof head);
memset(vis,,sizeof vis);
tot=;
for(int i=;i<=m;i++)
for(int j=;j<=m;j++){
if(i==j) continue;
bool flag=true;
for(int k=;k<n;k++)
if(!check(output[i][k],input[j][k])){
flag=false;
break;
}
if(flag){
insert(i+m,j,num[i]);
vis[i+m][j]=;
}
}
for(int i=;i<=m;i++){
insert(i,i+m,num[i]); //拆点
if(ck1(i)) insert(,i,num[i]);
if(ck2(i)) insert(i+m,*m+,num[i]);
}
printf("%d",dinic());
int cnt=;
for(int i=;i<=m;i++){
for(int j=head[i+m];j!=-;j=p[j].next)
if(vis[i+m][p[j].to]&&p[j].cap<num[i]) cnt++;
}
printf(" %d\n",cnt);
for(int i=;i<=m;i++){
for(int j=head[i+m];j!=-;j=p[j].next)
if(vis[i+m][p[j].to]&&p[j].cap<num[i]){
printf("%d %d %d\n",i,p[j].to,num[i]-p[j].cap);
}
}
}
return ;
}

最大流拆点——hdu2732,poj3436的更多相关文章

  1. poj 3498 March of the Penguins(最大流+拆点)

    题目大意:在南极生活着一些企鹅,这些企鹅站在一些冰块上,现在要让这些企鹅都跳到同一个冰块上.但是企鹅有最大的跳跃距离,每只企鹅从冰块上跳走时会给冰块造成损害,因此企鹅跳离每个冰块都有次数限制.找出企鹅 ...

  2. poj 2391 Ombrophobic Bovines, 最大流, 拆点, 二分, dinic, isap

    poj 2391 Ombrophobic Bovines, 最大流, 拆点, 二分 dinic /* * Author: yew1eb * Created Time: 2014年10月31日 星期五 ...

  3. POJ-3436 ACM Computer Factory---最大流+拆点

    题目链接: https://vjudge.net/problem/POJ-3436 题目大意: 每台电脑有p个组成部分,有n个工厂加工电脑.每个工厂对于进入工厂的半成品的每个组成部分都有要求,由p个数 ...

  4. hdu2732 最大流+拆点

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2732 题目给定一个场景,有n*m个方格,每个方格代表一个柱子,一个柱子可以承受不同次数的跳跃,开始时图 ...

  5. hdu2732 Leapin' Lizards 最大流+拆点

    Your platoon of wandering lizards has entered a strange room in the labyrinth you are exploring. As ...

  6. poj3436网络流之最大流拆点

    这题看了半天看不懂题意...还是看的网上题意写的 加一个源点一个汇点,把每个点拆成两个,这两个点的流量是v,其他联通的边都设为无穷大 输入没有1的点就与源点连接,输出只有1的点就与汇点连接 还有这个输 ...

  7. hdu4289 最小割最大流 (拆点最大流)

    最小割最大流定理:(参考刘汝佳p369)增广路算法结束时,令已标号结点(a[u]>0的结点)集合为S,其他结点集合为T=V-S,则(S,T)是图的s-t最小割. Problem Descript ...

  8. BZOJ-1877 晨跑 最小费用最大流+拆点

    其实我是不想做这种水题的QWQ,没办法,剧情需要 1877: [SDOI2009]晨跑 Time Limit: 4 Sec Memory Limit: 64 MB Submit: 1704 Solve ...

  9. BZOJ-1070 修车 最小费用最大流+拆点+略坑建图

    1070: [SCOI2007]修车 Time Limit: 1 Sec Memory Limit: 162 MB Submit: 3624 Solved: 1452 [Submit][Status] ...

随机推荐

  1. openwrt usb

    fdisk -l #以列表的形式,列出当前挂载盘的情况 for 属性规定 label 与哪个表单元素绑定 <form> <label for="male"> ...

  2. Exception一自定义异常

    异常体系的根类是:Throwable Throwable: Error:   重大的问题,我们处理不了.也不需要编写代码处理.比如说内存溢出. Exception:   一般性的错误,是需要我们对编写 ...

  3. delphi 键盘常用参数(PC端和手机端 安卓/IOS)

    常数名称(红色手机端) 十六进制值 十进制值 对应按键(手机端) Delphi编程表示(字符串型)_tzlin注 0 0 大键盘Delete键 #0 VK_LBUTTON 1 1 鼠标的左键 #1 V ...

  4. Delphi txt文件读取及写入

    简介:Delphi支持三种文件类型:文本文件.记录文件.无类型文件.文本文件的读...   在进行win32开发中对文件的读写是最常用的操作之一 Delphi 支持三种文件类型:  文本文件.记录文件 ...

  5. js简单图片切换

    <!DOCTYPE html> <html> <head> <meta charset="utf-8"/> <title> ...

  6. 「题解」:x

    问题 A: x 时间限制: 1 Sec  内存限制: 256 MB 题面 题面谢绝公开. 题解 赛时想到了正解并且对拍了很久.对拍没挂,但是评测姬表示我w0了……一脸懵逼. 不难证明,如果对于两个数字 ...

  7. NX二次开发-获取尺寸的附加文本UF_DRF_ask_appended_text

    #include <uf.h> #include <uf_drf.h> #include <uf_obj.h> #include <uf_part.h> ...

  8. 判断PC端浏览器类型

    if (browserInfo.type !== 'IE' || (browserInfo.type == 'IE' && Number(browserInfo.version) &g ...

  9. (转)OC学习笔记 @property的属性 strong 和 weak 理解

    在ObjectiveC里,用@property访问所有的实例变量.@property有一对属性:strong 和 weak.官方文档里的解释晦涩难懂:Stack Overflow里的用户RDC (ht ...

  10. var 更明确地表示一个变量被设置为零值

    创建一个变量并被初始化其为零值,习惯使用关键字var.这种做法是为了更明确地表示一个变量被设置为零值. 如果变量被初始化为某个非零值,就配合结构字面量和短变量操作符来创建变量. 零值 数值类型:0 字 ...