博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
[BZOJ2132] 圈地计划
阅读量:5916 次
发布时间:2019-06-19

本文共 2567 字,大约阅读时间需要 8 分钟。

Time Limit: 2 Sec  Memory Limit: 256 MB

Submit: 1350  Solved: 637
[][][]

Description

最近房地产商GDOI(Group of Dumbbells Or Idiots)从NOI(Nuts Old Idiots)手中得到了一块开发土地。据了解,这块土地是一块矩形的区域,可以纵横划分为N×M块小区域。GDOI要求将这些区域分为商业区和工业区来开发。根据不同的地形环境,每块小区域建造商业区和工业区能取得不同的经济价值。更具体点,对于第i行第j列的区域,建造商业区将得到Aij收益,建造工业区将得到Bij收益。另外不同的区域连在一起可以得到额外的收益,即如果区域(I,j)相邻(相邻是指两个格子有公共边)有K块(显然K不超过4)类型不同于(I,j)的区域,则这块区域能增加k×Cij收益。经过Tiger.S教授的勘察,收益矩阵A,B,C都已经知道了。你能帮GDOI求出一个收益最大的方案么?

Input

输入第一行为两个整数,分别为正整数N和M,分别表示区域的行数和列数;第2到N+1列,每行M个整数,表示商业区收益矩阵A;第N+2到2N+1列,每行M个整数,表示工业区收益矩阵B;第2N+2到3N+1行,每行M个整数,表示相邻额外收益矩阵C。第一行,两个整数,分别是n和m(1≤n,m≤100);

任何数字不超过1000”的限制

Output

输出只有一行,包含一个整数,为最大收益值。

Sample Input

3 3
1 2 3
4 5 6
7 8 9
9 8 7
6 5 4
3 2 1
1 1 1
1 3 1
1 1 1

Sample Output

81
【数据规模】
对于100%的数据有N,M≤100

HINT

 数据已加强,并重测--2015.5.15

思路

最小割;

黑白染色,对于每个黑点A,S->A:W商业,A->T:W工业,

对于每个白点B,S->B:W工业,B->T:W商业,对于每对有关系的两点A,B,A<–>B:c1+c2。

by:http://hzwer.com/2418.html

代码实现

1 #include
2 #include
3 const int maxn=300; 4 const int maxm=maxn*maxn; 5 inline int min_(int x,int y){
return x
tail){22 a=q[tail++];23 for(int i=h[a];i;i=en[i])24 if(!d[et[i]]&&ew[i]){25 d[et[i]]=d[a]+1;26 if(et[i]==t) return;27 q[head++]=et[i];28 }29 }30 }31 int ap(int k,int w){32 if(k==t) return w;33 int dw=w;34 for(int i=h[k];i&&dw;i=en[i])35 if(ew[i]&&d[et[i]]==d[k]+1){36 int wt=ap(et[i],min_(dw,ew[i]));37 ew[i]-=wt,ew[i^1]+=wt,dw-=wt;38 }39 if(w==dw) d[k]=0;40 return w-dw;41 }42 void Dinic(){
while(bfs(),d[t]) ans-=ap(s,1e5);}43 int main(){44 scanf("%d%d",&n,&m);45 s=0,t=1;46 for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) scanf("%d",&ind[i][j]),ans+=ind[i][j];47 for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) scanf("%d",&bus[i][j]),ans+=bus[i][j];48 for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) scanf("%d",&com[i][j]);49 for(int i=1;i<=n;i++)50 for(int j=1;j<=m;j++){51 if((i^j)&1) swap_(ind[i][j],bus[i][j]);52 add(s,i*m+j,ind[i][j]),add(i*m+j,s,0);53 add(i*m+j,t,bus[i][j]),add(t,i*m+j,0);54 if((i^j)&1) for(int k=0;k<4;k++){55 nh=i+hb[k],nl=j+lb[k];56 if(nh&&nh<=n&&nl&&nl<=m){57 add(i*m+j,nh*m+nl,com[i][j]+com[nh][nl]);58 add(nh*m+nl,i*m+j,com[i][j]+com[nh][nl]);59 ans+=com[i][j]+com[nh][nl];60 }61 }62 }63 Dinic();64 printf("%d",ans);65 return 0;66 }

 

转载于:https://www.cnblogs.com/J-william/p/7074605.html

你可能感兴趣的文章
C++虚函数表剖析
查看>>
谈下mysql预处理基础
查看>>
c++实现二叉搜索树
查看>>
关于前端的photoshop初探的学习笔记
查看>>
本地搭建ELK系统
查看>>
在 CentOS7 上安装 Zookeeper-3.4.9 服务
查看>>
Kafka consumer group位移重设
查看>>
SQL SERVER 服务启动失败
查看>>
多个IoC容器适配器设计及性能测试(Castle.Windsor Autofac Spring.Core)
查看>>
多线程编程2-NSOperation
查看>>
Linux命令:scp命令(文件上传和下载)
查看>>
logback配置详解
查看>>
如何构造树状 JSON 数据 JSON-Tree
查看>>
ICSharpCode.SharpZipLib工具压缩与解压缩zip文件
查看>>
mybatis中使用where in查询时的注意事项
查看>>
Hadoop2.2.0集群的HA高可靠的最简单配置
查看>>
oc49--@class
查看>>
spring 中 AOP 功能
查看>>
【GPU编解码】GPU硬编码
查看>>
elasticsearch如何安全重启
查看>>