题目背景

ZRQ在洞穴中准备采集矿物的时候遇险了!洞穴要塌了

题目来源:zhoutb2333

题目描述

整个洞穴是一个 \(N*N\) 的方格图,每个格子形如 \((X,Y),1 \le X,Y \le N\) 。其中 \(X\) 表示从上到下的行数,\(Y\) 表示从左到右的列数。 \((1,1)\) 在左上角,\((1,N)\) 在右上角, \((N,1)\) 在左下角, \((N,N)\) 在右下角。

满足 \(X+Y\) 为奇数格子的有一个不稳定度 \(V_{X,Y}\) , \(X+Y\) 为偶数的格子的不稳定度为 \(0\) 。

ZRQ现在手里恰巧有 \(M\) 个可以支撑洞穴的柱子,柱子的力量可以认为是无穷大。

只要支撑住了一个格子那么这个格子的不稳定度将降为 \(0\) 。

每个柱子是 \(L\) 型的,它除了要占据当前的格子外,还需要占据两个相邻的格子(这三个格子形成 \(L\) 型,可以选择任意方向放置,一共有 \(4\) 个方向)。

柱子占据相邻的格子不会降低其不稳定度(换句话说就是柱子只有在拐角处有力量)

有些格子的顶已经塌下来了,无法在其位置放置柱子了,这些格子也不能被占据了。这样已经塌了的格子有 \(K\) 个(他们的不稳定度都为 \(0\) ,即使 \(X+Y\) 为奇数,塌下来的格子的不稳定度也会为 \(0\) )。

ZRQ想问你,在放置一些柱子后 ,最小的不稳定度之和为多少(可以不将 \(M\) 个柱子都放完)。

输入输出格式

输入格式:

第一行三个整数 \(N,M,K\)

接下来 \(N\) 行每行 \(N\) 个整数,表示每个格子的不稳定度,保证 \(X+Y\) 为偶数的格子和已经塌下的格子的不稳定度为 \(0\)

接下来 \(K\) 行每行 \(2\) 个整数 \(X,Y\) ,表示已经塌下的格子的坐标。

输出格式:

一行一个整数,表示最小的不稳定度的和。

输入输出样例

输入样例#1:

3 3 1
0 1 0
2 0 1
0 1 0
1 3

输出样例#1:

3

输入样例#2:

3 3 4
0 2 0
0 0 4
0 3 0
1 3
2 1
2 2
3 1

输出样例#2:

9

说明

共 \(10\) 个测试点,每个点 \(10\) 分,计 \(100\) 分。

对于测试点 \(1\) ~ \(3\) ,有 \(1 \le N \le 6\)

对于测试点 \(4\) ~ \(7\) ,有 \(1 \le N \le 11\)

对于测试点 \(8\) ~ \(10\) ,有 \(1 \le N \le 50\)

对于所有测试点, \(0 \le M \le \frac{N^2}{3}, 0 \le K \le N^2, 0 \le V_{X,Y} \le 10^6\)

样例#1解释:

显然无法让任意两个不稳定的格子都被拐角覆盖,于是将 \((2,1)\) 用拐角覆盖住即可。这样剩余的不稳定度为 \(V_{1,2}+V_{2,3}+V_{3,2}=1+1+1=3\) 。

样例#2解释:

一个都放不下,这样剩余的不稳定度为 \(V_{1,2}+V_{2,3}+V_{3,2}=2+4+3=9\) 。

题解

考虑费用流。

为了方便描述,偶数格表示的是 为偶数的格子,奇数格表示的是为奇数的格子。

首先拐⻆处肯定放在有危险度的格子上。然后可以把这个 'L' 形石头看做是一条从奇数列的偶数格到奇数格再到偶数列的偶数格的一条路径。于是建四列点,把奇数列的偶数格放在第一列,每个奇数格拆成两个点分别放在第二列和第三列,偶数列的偶数格放在第四列。第一列到第二列是如果点是相邻的则连容量为 \(1\) 费用为 \(0\) 的边,第三列到第四列同理,第二列到第三列的相同点则连容量为 \(1\) 费用为负的危险度的边,然后源点向第一列,第四列向汇点连容量为 \(1\) 费用为 \(0\) 的边。

然后跑最小费用最大流,当此次增广的费用是正的了或者增广了次时就break,因为可能根本就放不下个石头,后面增广的费用是为了得到最大流而退流形成的,并不需要石头越多越好,我们只希望费用最小。

#include<bits/stdc++.h>
#define ui unsigned int
#define ll long long
#define db double
#define ld long double
#define ull unsigned long long
const int MAXN=100+10,MAXM=50000+10,inf=0x3f3f3f3f;
int n,m,k,e=1,beg[MAXN*MAXN*2],nex[MAXM<<1],to[MAXM<<1],cap[MAXM<<1],was[MAXM<<1],ans,G[MAXN][MAXN],T[MAXN][MAXN],prex[MAXN*MAXN*2],s,t,pres[MAXN*MAXN*2],M[4][MAXN][MAXN],tot,p[MAXN*MAXN*2],level[MAXN*MAXN*2];
std::queue<int> q;
template<typename T> inline void read(T &x)
{
T data=0,w=1;
char ch=0;
while(ch!='-'&&(ch<'0'||ch>'9'))ch=getchar();
if(ch=='-')w=-1,ch=getchar();
while(ch>='0'&&ch<='9')data=((T)data<<3)+((T)data<<1)+(ch^'0'),ch=getchar();
x=data*w;
}
template<typename T> inline void write(T x,char ch='\0')
{
if(x<0)putchar('-'),x=-x;
if(x>9)write(x/10);
putchar(x%10+'0');
if(ch!='\0')putchar(ch);
}
template<typename T> inline void chkmin(T &x,T y){x=(y<x?y:x);}
template<typename T> inline void chkmax(T &x,T y){x=(y>x?y:x);}
template<typename T> inline T min(T x,T y){return x<y?x:y;}
template<typename T> inline T max(T x,T y){return x>y?x:y;}
inline void insert(int x,int y,int z,int w)
{
to[++e]=y;
nex[e]=beg[x];
beg[x]=e;
cap[e]=z;
was[e]=w;
to[++e]=x;
nex[e]=beg[y];
beg[y]=e;
cap[e]=0;
was[e]=-w;
}
inline bool bfs()
{
memset(level,inf,sizeof(level));
level[s]=0;
p[s]=1;
q.push(s);
while(!q.empty())
{
int x=q.front();
q.pop();
p[x]=0;
for(register int i=beg[x];i;i=nex[i])
if(cap[i]&&level[to[i]]>level[x]+was[i])
{
level[to[i]]=level[x]+was[i];
if(!p[to[i]])p[to[i]]=1,q.push(to[i]);
prex[to[i]]=x;
pres[to[i]]=i;
}
}
return level[t]<0;
}
inline void dfs()
{
int f=inf;
for(register int i=t;i!=s;i=prex[i])chkmin(f,cap[pres[i]]);
for(register int i=t;i!=s;i=prex[i])ans+=f*was[pres[i]],cap[pres[i]]-=f,cap[pres[i]^1]+=f;
}
int main()
{
read(n);read(m);read(k);
for(register int i=1;i<=n;++i)
for(register int j=1;j<=n;++j)read(G[i][j]),ans+=G[i][j];
for(register int i=1;i<=k;++i)
{
int x,y;read(x);read(y);
T[x][y]=1;
}
for(register int i=1;i<=n;++i)
for(register int j=1;j<=n;++j)
if((i+j)&1)
{
M[1][i][j]=++tot,M[2][i][j]=++tot;
if(!T[i][j])insert(M[1][i][j],M[2][i][j],1,-G[i][j]);
}
else M[((i&1)?0:3)][i][j]=++tot;
s=++tot,t=++tot;
for(register int i=1;i<=n;++i)
for(register int j=1;j<=n;++j)
if(T[i][j])continue;
else if((i+j)&1^1)
{
if(i&1)
{
if(j!=1&&!T[i][j-1])insert(M[0][i][j],M[1][i][j-1],1,0);
if(j!=n&&!T[i][j+1])insert(M[0][i][j],M[1][i][j+1],1,0);
if(i!=1&&!T[i-1][j])insert(M[0][i][j],M[1][i-1][j],1,0);
if(i!=n&&!T[i+1][j])insert(M[0][i][j],M[1][i+1][j],1,0);
insert(s,M[0][i][j],1,0);
}
else
{
if(j!=1&&!T[i][j-1])insert(M[2][i][j-1],M[3][i][j],1,0);
if(j!=n&&!T[i][j+1])insert(M[2][i][j+1],M[3][i][j],1,0);
if(i!=1&&!T[i-1][j])insert(M[2][i-1][j],M[3][i][j],1,0);
if(i!=n&&!T[i+1][j])insert(M[2][i+1][j],M[3][i][j],1,0);
insert(M[3][i][j],t,1,0);
}
}
while(bfs()&&m--)dfs();
write(ans,'\n');
return 0;
}

【刷题】洛谷 P4142 洞穴遇险的更多相关文章

  1. 2018.10.30 一题 洛谷4660/bzoj1168 [BalticOI 2008]手套——思路!问题转化与抽象!+单调栈

    题目:https://www.luogu.org/problemnew/show/P4660 https://www.lydsy.com/JudgeOnline/problem.php?id=1168 ...

  2. AC日记——大爷的字符串题 洛谷 P3709

    大爷的字符串题 思路: 莫队,需开O2,不开50: 代码: #include <bits/stdc++.h> using namespace std; #define maxn 20000 ...

  3. Mychael原创题 洛谷T23923 Mychaelの水题 【题解】

    原题链接 题目大意: 有来自三个地区的人各a,b,c位,他们排成了一排.请问有多少种不同类型的排法,使得相邻的人都来自不同的地区 \(a,b,c<=200\) 答案取模 题解 弱弱的标程解法 设 ...

  4. 最短路径Dijkstra算法模板题---洛谷P3371 【模板】单源最短路径(弱化版)

    题目背景 本题测试数据为随机数据,在考试中可能会出现构造数据让SPFA不通过,如有需要请移步 P4779. 题目描述 如题,给出一个有向图,请输出从某一点出发到所有点的最短路径长度. 输入格式 第一行 ...

  5. 洛谷P5098 洞穴里的牛之三

    题目 贪心,可以用分类讨论的方法,可以得出如果\(n^2\)枚举则会过不了,而我们观察原题中的式子,有: \(∣x1−x2∣+∣y1−y2∣\) 发现式子中的绝对值很恶心,而考虑如果没有绝对值的话会有 ...

  6. [网络流24题] 洛谷P2761 软件补丁问题

    题意:某公司发现其研制的一个软件中有 n个错误,随即为该软件发放了一批共 m 个补丁程序.对于每一个补丁 i ,都有 2 个与之相应的错误集合 B1(i)和 B2(i),使得仅当软件包含 B1(i)中 ...

  7. 高精度加法——经典题 洛谷p1601

    题目背景 无 题目描述 高精度加法,x相当于a+b problem,[b][color=red]不用考虑负数[/color][/b] 输入输出格式 输入格式: 分两行输入a,b<=10^500 ...

  8. 用Python写算法题--洛谷P1149 火柴棒等式

    题目 题目来源 P1149 火柴棒等式,https://www.luogu.org/problem/P1149 题目描述 给你n根火柴棍,你可以拼出多少个形如"A+B=C"的等式? ...

  9. dijkstra模板题 洛谷1339 邻接图建边

    题目链接:https://www.luogu.com.cn/problem/P1339 朴素dijkstra算法的复杂度是O(n^2),用堆优化的dijkstra复杂度是O(nlogn)的.在本题中前 ...

随机推荐

  1. Nginx入门篇(四)之常用配置解析

    1.Nginx状态信息功能 Nginx的模块当中有一个ngx_http_stub_status_module模块,这个模块主要记录Nginx的基本访问信息,要使用该模块,需要在编译的时候增加http_ ...

  2. svn 冲突处理

    C:\workspace\test>svn upConflict discovered in 'test.txt'.Select: (p) postpone, (df) diff-full, ( ...

  3. 深入浅出之-route命令实战使用指南

    本博文的视频讲解已发布:http://oldboy.blog.51cto.com/2561410/1119453 缘起:本文为老男孩linux培训第七次课前考试题及参考答案,有朋友在看完http:// ...

  4. 各web服务器的特点和优势

    1.Tomcat 和 Jetty 面向java语言 天生就是重量级的web服务器.性能一般 2.IIS 只能在windows平台运行,windows作为服务器在稳定性与其他一些性能上不如类unix操作 ...

  5. Numpy入门笔记第二天

    # 数组的组合 import numpy as np arr1 = np.arange(5) arr2 = np.arange(3) print arr1 print arr2 [0 1 2 3 4] ...

  6. echarts.js使用心得--demo

    首先要感谢一下我的公司,因为公司需求上面的新颖(奇葩)的需求,让我有幸可以学习到一些好玩有趣的前端技术. 废话不多时 , 直接开始. 第一步: 导入echarts.js文件 下载地址:http://e ...

  7. python format用法详解

    #常用方法:print('{0},{1}'.format('zhangk', 32)) print('{},{},{}'.format('zhangk','boy',32)) print('{name ...

  8. loadrunner socket协议问题归纳(1)

    前段时间测了loadrunner直接发送报文到socket上的性能测试.在此,稍微回顾整理下. 与socket通讯,有两种方式,一种是建立长连接,建立后,不停的发送,接收.另外一种是建立短连接,建立连 ...

  9. SQL连接的方法

    1.创建连接字符串 string con = "Data Source=127.0.0.1;Initial Catalog=dingdan;Integrated Security=True& ...

  10. 按照Right-BICEP要求设计的测试用例

    测试用例: 测试方法:Right-BICEP 测试要求: Right-结果是否正确? B-是否所有的边界条件都是正确的? P-是否满足性能要求? 题目是否有重复? 数量是否可定制? 数值范围是否可定制 ...