题面:洛谷传送门 BZOJ传送门

最大流神题

把点权转化为边权,切糕里每个点$(i,j,k)$向$(i,j,k+1)$连一条流量为$v(i,j,k)$的边

源点$S$向第$1$层的点连边,第$R+1$层的点向$T$连边,流量均为$inf$

跑最大流,最大流的流量就是答案

因为每条纵轴都取了最小的$v$,被割掉的边就是最小的$v$所在的边

然而题目里还有限制,相邻两个纵轴取值的位置相差的距离不能超过$D$

如何处理这个限制呢?

每个点$(i,j,k)$向$(x,y,k-D)$连流量为$inf$的边,$(x,y)$是$(i,j)$相邻的纵轴

假设纵轴$(i,j)$的割点是$(i,j,k)$

如果$(x,y)$的割点在$(x,y,k-D)$下面,一定会有一条流量从纵轴$(i,j)$流到$(x,y)$里,然后向上流到汇点$T$

巧妙地解决了距离的限制问题

 #include <cstdio>
#include <cstring>
#include <algorithm>
#define N1 67010
#define M1 400010
#define L1 45
using namespace std;
const int inf=0x3f3f3f3f; int gint()
{
int ret=,fh=;char c=getchar();
while(c<''||c>''){if(c=='-')fh=-;c=getchar();}
while(c>=''&&c<=''){ret=ret*+c-'';c=getchar();}
return ret*fh;
}
struct Edge{
int to[M1<<],nxt[M1<<],flow[M1<<],head[N1],cte;
void ae(int u,int v,int f)
{
cte++; to[cte]=v; nxt[cte]=head[u];
head[u]=cte; flow[cte]=f;
}
}e; int dep[N1],que[M1],cur[N1],n,m,h,D,hd,tl,S,T;
int bfs()
{
int x,j,v;
memset(dep,-,sizeof(dep)); memcpy(cur,e.head,sizeof(cur));
hd=,tl=; que[++tl]=S; dep[S]=;
while(hd<=tl)
{
x=que[hd++];
for(j=e.head[x];j;j=e.nxt[j])
{
v=e.to[j];
if( dep[v]==- && e.flow[j]> )
{
dep[v]=dep[x]+;
que[++tl]=v;
}
}
}
return dep[T]!=-;
}
int dfs(int x,int limit)
{
int j,v,flow,ans=;
if(!limit||x==T) return limit;
for(j=cur[x];j;j=e.nxt[j])
{
v=e.to[j]; cur[x]=j;
if( dep[v]==dep[x]+ && (flow=dfs(v,min(limit,e.flow[j]))) )
{
e.flow[j]-=flow; limit-=flow;
e.flow[j^]+=flow; ans+=flow;
if(!limit) break;
}
}
return ans;
}
int Dinic()
{
int mxflow=,j,v,ans=;
while(bfs())
mxflow+=dfs(S,inf);
return mxflow;
} int xx[]={-,,,},yy[]={,,,-};
int v[L1][L1][L1],id[L1][L1][L1];
inline int check(int x,int y){return (x<||y<||x>n||y>m)?:;} int main()
{
scanf("%d%d%d%d",&n,&m,&h,&D);
int i,j,k,x,y,w,p; e.cte=; S=; T=n*m*(h+)+;
for(k=;k<=h+;k++) for(i=;i<=n;i++) for(j=;j<=m;j++) id[k][i][j]=(k-)*n*m+(i-)*m+j;
for(k=;k<=h;k++) for(i=;i<=n;i++) for(j=;j<=m;j++)
{
w=v[k][i][j]=gint(), x=id[k][i][j];
e.ae(x,x+n*m,w), e.ae(x+n*m,x,);
if(k<=D) continue;
//x+=n*m;
for(p=;p<;p++)
{
if(!check(i+xx[p],j+yy[p])) continue;
y=id[k-D][i+xx[p]][j+yy[p]];
e.ae(x,y,inf); e.ae(y,x,);
}
}
for(i=;i<=n;i++) for(j=;j<=m;j++) e.ae(S,id[][i][j],inf), e.ae(id[][i][j],S,);
for(i=;i<=n;i++) for(j=;j<=m;j++) e.ae(id[h+][i][j],T,inf), e.ae(T,id[h+][i][j],);
printf("%d\n",Dinic());
return ;
}

BZOJ 3144 [HNOI2013]切糕 (最大流+巧妙的建图)的更多相关文章

  1. BZOJ 3144: [Hnoi2013]切糕

    3144: [Hnoi2013]切糕 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 1495  Solved: 819[Submit][Status] ...

  2. bzoj 3144: [Hnoi2013]切糕 最小割

    3144: [Hnoi2013]切糕 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 681  Solved: 375[Submit][Status] ...

  3. [BZOJ 3144] [Hnoi2013] 切糕 【最小割】

    题目链接:BZOJ - 3144 题目分析 题意:在 P * Q 的方格上填数字,可以填 [1, R] . 在 (x, y) 上填 z 会有 V[x][y][z] 的代价.限制:相邻两个格子填的数字的 ...

  4. 洛谷 P3227 BZOJ 3144 [HNOI2013]切糕

    题目描述 经过千辛万苦小 A 得到了一块切糕,切糕的形状是长方体,小 A 打算拦腰将切糕切成两半分给小 B.出于美观考虑,小 A 希望切面能尽量光滑且和谐.于是她找到你,希望你能帮她找出最好的切割方案 ...

  5. [NOI2008][bzoj1061] 志愿者招募 [费用流+巧妙的建图]

    题面 传送门 思路 引入:网络流? 看到这道题,第一想法是用一个dp来完成决策 但是,显然这道题的数据并不允许我们进行dp,尤其是有10000种志愿者的情况下 那么我们就要想别的办法来解决: 贪心?这 ...

  6. 【刷题】BZOJ 3144 [Hnoi2013]切糕

    Description Input 第一行是三个正整数P,Q,R,表示切糕的长P. 宽Q.高R.第二行有一个非负整数D,表示光滑性要求.接下来是R个P行Q列的矩阵,第z个 矩阵的第x行第y列是v(x, ...

  7. bzoj 3144 [Hnoi2013]切糕——最小割

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3144 一根纵轴上切一个点,可以把一根纵轴上的点连成一串来体现.自己的写法是每个点连向前一个点 ...

  8. BZOJ 3144 [Hnoi2013]切糕 ——网络流

    [题目分析] 网络流好题! 从割的方面来考虑问题往往会得到简化. 当割掉i,j,k时,必定附近的要割在k-D到k+D上. 所以只需要建两条inf的边来强制,如果割不掉强制范围内的时候,原来的边一定会换 ...

  9. bzoj 3144 [Hnoi2013]切糕【最小割+dinic】

    都说了是'切'糕所以是最小割咯 建图: 每个点向下一层连容量为这个点的val的边,S向第一层连容量为inf的边,最后一层向T连容量为自身val的边,即割断这条边相当于\( f(i,j) \)选择了当前 ...

随机推荐

  1. windows终端 进入文件夹

    盘符: 例如想进入D盘 d: cd 进入到当前盘某个目录.cd \ 进入当前盘根目录cd \windows 进入到当前盘Windows目录cd.. 退出到上一级目录 注:进入含有特殊字符目录时需要加引 ...

  2. php模拟并发

    原文: http://blog.csdn.net/zhang_xinglong/article/details/16339867 ----------------------------------- ...

  3. HDU 4906 Our happy ending (状压DP)

    HDU 4906 Our happy ending pid=4906" style="">题目链接 题意:给定n个数字,每一个数字能够是0-l,要选当中一些数字.然 ...

  4. poj2299--归并排序求逆序数

    /** \brief poj2299  *  * \param date 2014/8/5  * \param state AC  * \return memory 4640K time 3250ms ...

  5. 推断一个点是否在某个区域内。百度,高德,腾讯都能用。(php版)

    watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQv/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/ ...

  6. poj 3913(水)

    Description You have devised a new encryption technique which encodes a message by inserting between ...

  7. 名词解释 —— 抄送(cc)、银弹(silver bullet)

    抄送(Carbon Copy,carbon copy 本身的含义是复写本,副本),又简称为 CC. 在现代汉语中,含有抄写与送达的双重意思. 在网络术语中,抄送就是将邮件同时发送给收信人以外的人, 用 ...

  8. (Go)01.Windows 安装 Go语言开发环境以及使用

    一.Go语言下载 go语言官方下载地址:https://golang.org/dl/ 找到适合你系统的版本下载,本人下载的是windows msi版本.也可以下载Source自己更深层次研究go语言 ...

  9. WPF中ListBox ListView数据翻页浏览笔记(强调:是数据翻页,非翻页动画)

    ListBox和ListView在应用中,常常有需求关于每页显示固定数量的数据,然后通过Timer自动或者手动翻页操作,本文介绍到的就是该动作的实现. 一.重点 对于ListBox和ListView来 ...

  10. Python 生成requirement 使用requirements.txt

    第一步:python项目中必须包含一个 requirements.txt 文件,用于记录所有依赖包及其精确的版本号.以便新环境部署. requirements.txt可以通过pip命令自动生成和安装 ...