bzoj3774
这算是最小割中比较难的吧
看到选取显然最小割
看到上下左右四个点我感觉肯定和染色相关
注意每个点的收益获得条件是[或],因此我们考虑拆点i', i,分别表示通过四周控制和控制本身的代价
连边s-->i 流量为选择该点的代价; i-->i' 流量为该点的收益; i'到上下左右的j,流量为正无穷,表示另一个条件
这样,要获得收益便一定要割断一边,就满足了或的性质
注意,另一种颜色的连边与这种颜色相反,由于染色可以得到二分图
所以另一种颜色的连边反过来建即可
const inf=;
dx:array[..] of longint=(,,-,);
dy:array[..] of longint=(,-,,); type node=record
po,next,flow:longint;
end; var e:array[..] of node;
numh,h,cur,p,pre,d:array[..] of longint;
a:array[..,..] of longint;
ans,i,j,x,y,len,t,n,m,k:longint; function min(a,b:longint):longint;
begin
if a>b then exit(b) else exit(a);
end; procedure add(x,y,f:longint);
begin
inc(len);
e[len].po:=y;
e[len].flow:=f;
e[len].next:=p[x];
p[x]:=len;
end; procedure build(x,y,f:longint);
begin
add(x,y,f);
add(y,x,);
end; function sap:longint;
var i,j,u,neck,tmp,q:longint;
begin
for i:= to t do
cur[i]:=p[i];
sap:=;
u:=;
neck:=inf;
numh[]:=t+;
while h[]<t+ do
begin
i:=cur[u];
d[u]:=neck;
while i<>- do
begin
j:=e[i].po;
if (e[i].flow>) and (h[u]=h[j]+) then
begin
neck:=min(neck,e[i].flow);
pre[j]:=u;
cur[u]:=i;
u:=j;
if u=t then
begin
sap:=sap+neck;
while u<> do
begin
u:=pre[u];
j:=cur[u];
dec(e[j].flow,neck);
inc(e[j xor ].flow,neck);
end;
neck:=inf;
end;
break;
end;
i:=e[i].next;
end;
if i=- then
begin
dec(numh[h[u]]);
if numh[h[u]]= then exit;
tmp:=t;
q:=-;
i:=p[u];
while i<>- do
begin
j:=e[i].po;
if e[i].flow> then
if h[j]<tmp then
begin
tmp:=h[j];
q:=i;
end;
i:=e[i].next;
end;
cur[u]:=q;
h[u]:=tmp+;
inc(numh[h[u]]);
if u<> then
begin
u:=pre[u];
neck:=d[u];
end;
end;
end;
end; begin
len:=-;
fillchar(p,sizeof(p),);
readln(n,m);
t:=*n*m+;
for i:= to n do
for j:= to m do
begin
read(x);
inc(k); a[i,j]:=k;
if (i+j) mod = then build(,a[i,j],x)
else build(a[i,j],t,x);
end; for i:= to n do
for j:= to m do
begin
read(x);
ans:=ans+x;
if (i+j) mod = then build(a[i,j],a[i,j]+n*m,x)
else build(a[i,j]+n*m,a[i,j],x);
end; for i:= to n do
for j:= to m do
begin
if (i+j) mod = then
begin
for k:= to do
begin
x:=i+dx[k];
y:=j+dy[k];
if (x<=) or (x>n) or (y<=) or (y>m) then continue;
build(a[i,j]+n*m,a[x,y],inf);
end;
end
else begin
for k:= to do
begin
x:=i+dx[k];
y:=j+dy[k];
if (x<=) or (x>n) or (y<=) or (y>m) then continue;
build(a[x,y],a[i,j]+n*m,inf);
end;
end;
end; writeln(ans-sap);
end.
bzoj3774的更多相关文章
- 【BZOJ3774】最优选择 最小割
[BZOJ3774]最优选择 Description 小N手上有一个N*M的方格图,控制某一个点要付出Aij的代价,然后某个点如果被控制了,或者他周围的所有点(上下左右)都被控制了,那么他就算是被选择 ...
- 【bzoj3774】最优选择 网络流最小割
题目描述 小N手上有一个N*M的方格图,控制某一个点要付出Aij的代价,然后某个点如果被控制了,或者他周围的所有点(上下左右)都被控制了,那么他就算是被选择了的.一个点如果被选择了,那么可以得到Bij ...
- bzoj3774 最优选择
题目描述: 小N手上有一个N*M的方格图,控制某一个点要付出Aij的代价,然后某个点如果被控制了,或者他周围的所有点(上下左右)都被控制了,那么他就算是被选择了的.一个点如果被选择了,那么可以得到Bi ...
- Day5网络流
算法 无源汇上下界可行流 先强制流过l的流量 从s到每个正权点连流量为l的流量 从每个负权点向t连-l的流量 如果容量为0,则不连边 有源汇上下界最大流 去掉下界 先求出可行流 再求S到T的最大流 有 ...
随机推荐
- listView异步处理图片下载缓存
package cn.wangmeng.test; import java.io.File;import java.io.FileOutputStream;import java.io.IOExcep ...
- 使用FileResult导出txtl数据文件
public FileResult ExportMobileNoTxt(SearchClientModel model){ var sbTxt = new StringBuilder(); ; i & ...
- dapper 自定义数据库字段和代码中Model字段不一致时候的mapping方法
namespace YourNamespace { /// <summary> /// Uses the Name value of the ColumnAttribute specifi ...
- Spark Tungsten揭秘 Day1 jvm下的性能优化
Spark Tungsten揭秘 Day1 jvm下的性能优化 今天开始谈下Tungsten,首先我们需要了解下其背后是符合了什么样的规律. jvm对分布式天生支持 整个Spark分布式系统是建立在分 ...
- 从浏览器启动应用程序 - Application URL
关键字:Browser,Application,URL Protocol,Windows,Mac,IE,Chrome,Safari. OS: Windows 7, OS X Yosemite. Win ...
- Torry的困惑(基本型)
#include<stdio.h> int main() { long long i,j; int n; //用于记录输入的要进行乘积的质数的个数 ; //用于记录前n个质数的乘积,并初始 ...
- Linux下mail/mailx命令发送邮件
最近看到项目中经常会用mail/mailx命令发送由java程序生成的report,比较新鲜.下面就简单介绍下mail/mailx命令用法.本文以mail命令举例(mail/mailx)效果都是一样的 ...
- Relay log read failure
root@localhost > show slave status\G*************************** 1. row ************************** ...
- 区间型动规--石子归并(Pascal)
题目描述 Description 有n堆石子排成一列,每堆石子有一个重量w[i], 每次合并可以合并相邻的两堆石子,一次合并的代价为两堆石子的重量和w[i]+w[i+1].问安排怎样的合并顺序,能够使 ...
- 人生规划和GTD——“知”、“得”与“合”
写在前面:非常不错的一篇GTD入门以及人生目标与规划的文章,值得收藏. 本文来自 零折 作为<小强升职记>的读书感悟,给我自己.作为分享,也送给或许需要的给你. 我不知道你是否真的需要.但 ...