洛谷P4486 Kakuro
题意:你有一个棋盘,某些格子是限制条件,形如"从这里开始下面所有连续空格的和为a"或"从这里开始向右的所有连续空格之和为b"一个格子可以同时拥有两个限制条件。
每个数都必须是正整数。
现在你可以把某些格子加/减1,并花费相应的代价。可以操作无数次。求把棋盘变得合法的最小代价。
解:没想出来,看了题解......
一开始想了数字和条件构成二分图,又想了行列连边,但是始终建不出图来。
行列连边。
因为既可以加又可以减不好搞,我们可以先全部转换成满足条件的最小值,然后往上加。
从最小值到初始值的时候,边权为负。之后边权为正。
不可修改的地方边权为INF。
然后跑一个最小费用可行流就是答案。
如何判断无解?
考虑每条边,如果有的边费用为INF但是有流量,就不合法。
#include <cstdio>
#include <algorithm>
#include <queue>
#include <cstring> typedef long long LL;
const LL N = , M = , INF = 0x3f3f3f3f, J = ; struct Edge {
LL nex, v, c, len;
}edge[N << ]; LL top = ; LL e[N], d[N], vis[N], pre[N], flow[N];
std::queue<LL> Q;
LL fr[J][J], val[J][J], v2[J][J], cst[J][J], c2[J][J], m; inline void add(LL x, LL y, LL z, LL w) {
top++;
edge[top].v = y;
edge[top].c = z;
edge[top].len = w;
edge[top].nex = e[x];
e[x] = top; top++;
edge[top].v = x;
edge[top].c = ;
edge[top].len = -w;
edge[top].nex = e[y];
e[y] = top;
return;
} inline bool SPFA(LL s, LL t) {
memset(d, 0x3f, sizeof(d));
d[s] = ;
flow[s] = INF;
vis[s] = ;
Q.push(s);
while(!Q.empty()) {
LL x = Q.front();
Q.pop();
vis[x] = ;
for(LL i = e[x]; i; i = edge[i].nex) {
LL y = edge[i].v;
if(edge[i].c && d[y] > d[x] + edge[i].len) {
d[y] = d[x] + edge[i].len;
pre[y] = i;
flow[y] = std::min(flow[x], edge[i].c);
if(!vis[y]) {
vis[y] = ;
Q.push(y);
}
}
}
}
return d[t] < INF;
} inline void update(LL s, LL t) {
LL temp = flow[t];
while(t != s) {
LL i = pre[t];
edge[i].c -= temp;
edge[i ^ ].c += temp;
t = edge[i ^ ].v;
}
return;
} inline LL solve(LL s, LL t, LL &cost) {
LL ans = ;
cost = ;
while(SPFA(s, t)) {
if(d[t] > ) {
break;
}
ans += flow[t];
cost += flow[t] * d[t];
update(s, t);
}
return ans;
} inline LL id(LL x, LL y) {
return (x - ) * m + y;
} int main() {
LL n, use = ;
scanf("%lld%lld", &n, &m);
for(LL i = ; i <= n; i++) {
for(LL j = ; j <= m; j++) {
scanf("%lld", &fr[i][j]);
}
}
for(LL i = ; i <= n; i++) {
for(LL j = ; j <= m; j++) {
if(fr[i][j] == ) {
continue;
}
else if(fr[i][j] == ) {
scanf("%lld", &val[i][j]);
}
else if(fr[i][j] == ) {
scanf("%lld", &v2[i][j]);
}
else if(fr[i][j] == ) {
scanf("%lld%lld", &val[i][j], &v2[i][j]);
}
else {
scanf("%lld", &val[i][j]);
}
}
}
for(LL i = ; i <= n; i++) {
for(LL j = ; j <= n; j++) {
if(fr[i][j] == ) {
continue;
}
else if(fr[i][j] == ) {
scanf("%lld", &cst[i][j]);
}
else if(fr[i][j] == ) {
scanf("%lld", &c2[i][j]);
}
else if(fr[i][j] == ) {
scanf("%lld%lld", &cst[i][j], &c2[i][j]);
}
else {
scanf("%lld", &cst[i][j]);
}
if(cst[i][j] == -) {
cst[i][j] = INF;
}
if(c2[i][j] == -) {
c2[i][j] = INF;
}
}
}
// read over
LL lm = n * m;
LL s = lm * + ;
LL t = s + ;
for(LL i = ; i <= n; i++) {
for(LL j = ; j <= m; j++) {
if(fr[i][j] == ) {
continue;
}
if(fr[i][j] == || fr[i][j] == ) {
// id(i, j)
LL cnt = ;
for(LL k = i + ; k <= n; k++) {
if(fr[k][j] == ) {
cnt++;
}
else {
break;
}
}
// val[i][j] - cnt
if(val[i][j] > cnt) {
add(s, id(i, j), val[i][j] - cnt, -cst[i][j]);
}
add(s, id(i, j), INF, cst[i][j]);
use += cst[i][j] * abs(val[i][j] - cnt);
}
if(fr[i][j] == || fr[i][j] == ) {
LL cnt = ;
for(LL k = j + ; k <= m; k++) {
if(fr[i][k] == ) {
cnt++;
}
else {
break;
}
}
if(v2[i][j] > cnt) {
add(id(i, j) + lm, t, v2[i][j] - cnt, -c2[i][j]);
}
add(id(i, j) + lm, t, INF, c2[i][j]);
use += c2[i][j] * abs(v2[i][j] - cnt);
}
if(fr[i][j] == ) {
LL a, b;
for(LL k = i - ; k >= ; k--) {
if(fr[k][j] == || fr[k][j] == ) {
a = id(k, j);
break;
}
}
for(LL k = j - ; k >= ; k--) {
if(fr[i][k] == || fr[i][k] == ) {
b = id(i, k) + lm;
break;
}
}
if(val[i][j] > ) {
add(a, b, val[i][j] - , -cst[i][j]);
}
add(a, b, INF, cst[i][j]);
use += cst[i][j] * abs(val[i][j] - );
}
}
} LL ans;
solve(s, t, ans);
ans += use; /*if(ans >= INF) {
puts("-1");
return 0;
}*/
for(int i = ; i <= top; i += ) {
if(abs(edge[i].len) == INF && (edge[i].c && edge[i ^ ].c)) {
puts("-1");
return ;
}
} printf("%lld", ans);
return ;
}
AC代码
思考:能否不转换为最小?好像无法判断是否合法...
洛谷P4486 Kakuro的更多相关文章
- Solution -「BJWC 2018」「洛谷 P4486」Kakuro
		
\(\mathcal{Description}\) Link. 有一个 \(n\times m\) 的网格图,其中某些格子被主对角线划成两个三角形,称这样的格子为特殊格:初始时,除了一些障碍格 ...
 - 洛谷1640 bzoj1854游戏 匈牙利就是又短又快
		
bzoj炸了,靠离线版题目做了两道(过过样例什么的还是轻松的)但是交不了,正巧洛谷有个"大牛分站",就转回洛谷做题了 水题先行,一道傻逼匈牙利 其实本来的思路是搜索然后发现写出来类 ...
 - 洛谷P1352  codevs1380 没有上司的舞会——S.B.S.
		
没有上司的舞会 时间限制: 1 s 空间限制: 128000 KB 题目等级 : 钻石 Diamond 题目描述 Description Ural大学有N个职员,编号为1~N.他们有 ...
 - 洛谷P1108 低价购买[DP | LIS方案数]
		
题目描述 “低价购买”这条建议是在奶牛股票市场取得成功的一半规则.要想被认为是伟大的投资者,你必须遵循以下的问题建议:“低价购买:再低价购买”.每次你购买一支股票,你必须用低于你上次购买它的价格购买它 ...
 - 洛谷 P2701 [USACO5.3]巨大的牛棚Big Barn Label:二维数组前缀和 你够了 这次我用DP
		
题目背景 (USACO 5.3.4) 题目描述 农夫约翰想要在他的正方形农场上建造一座正方形大牛棚.他讨厌在他的农场中砍树,想找一个能够让他在空旷无树的地方修建牛棚的地方.我们假定,他的农场划分成 N ...
 - 洛谷P1710 地铁涨价
		
P1710 地铁涨价 51通过 339提交 题目提供者洛谷OnlineJudge 标签O2优化云端评测2 难度提高+/省选- 提交 讨论 题解 最新讨论 求教:为什么只有40分 数组大小一定要开够 ...
 - 洛谷P1371 NOI元丹
		
P1371 NOI元丹 71通过 394提交 题目提供者洛谷OnlineJudge 标签云端评测 难度普及/提高- 提交 讨论 题解 最新讨论 我觉得不需要讨论O long long 不够 没有取 ...
 - 洛谷P1538迎春舞会之数字舞蹈
		
题目背景 HNSDFZ的同学们为了庆祝春节,准备排练一场舞会. 题目描述 在越来越讲究合作的时代,人们注意的更多的不是个人物的舞姿,而是集体的排列. 为了配合每年的倒计时,同学们决定排出——“数字舞蹈 ...
 - 洛谷八月月赛Round1凄惨记
		
个人背景: 上午9:30放学,然后因为学校举办读书工程跟同学去书城选书,中午回来开始打比赛,下午又回老家,中间抽出一点时间调代码,回家已经8:50了 也许是7月月赛时“连蒙带骗”AK的太幸运然而因同学 ...
 
随机推荐
- Panorama——H5实现全景图片原理
			
前言 H5是怎么实现全景图片播放呢? 正文 全景图的基本原理即 "等距圆柱投影",这是一种将球体上的各个点投影到圆柱体的侧面上的一种投影方式,投影后再展开就是一张 2:1 的矩形图 ...
 - 萌新程序媛的首个作品,基于NoSQL的内容管理及低码开发平台
			
尽管入行有一段时间了,但之前还从来没想过要开发一款完整的软件产品.这个我跟朋友开发的第一款软件,希望大家帮我们多宣传推广.首个版本肯定有很多的不足,大家也给我们多提意见,还有很多规划中的功能要在之后的 ...
 - 基于Shader实现的UGUI描边解决方案
			
基于Shader实现的UGUI描边解决方案 前言 大扎好,我系狗猥.当大家都以为我鸽了的时候,我又出现了,这也是一种鸽.创业两年失败后归来,今天想给大家分享一个我最近研究出来的好康的,比游戏还刺激,还 ...
 - 开源一个最近写的spring与mongodb结合的demo(spring-mongodb-demo)
			
由于工作需要,给同事们分享了一下mongodb的使用,其中主要就是做了一个spring-data+mongodb的小例子,本着分享的精神,就上传到了github.com上,有需要的同学请移步githu ...
 - zookeeper应用
			
1. 下载zookeeper-3.4.10.tar.gz 2.tar zxvf zoo*.tar.gz 3. cd /usr/local/zookeeper/zookeeper-3.4.10/conf ...
 - linux内核分析第三次实验
			
http://blog.sina.com.cn/s/blog_78e559950102wo67.html
 - js生成uuid代码
			
function uuid() { var s = []; var hexDigits = "0123456789abcdef"; for (var i = 0; i < 3 ...
 - 实训五(Cocos2dx-3.x 打包apk再理解)
			
问题说明:Unable to resolve target 'android-10' SDK版本与Cocos项目默认的版本不相符 如果只是执行 cocos compile -p android 只是执 ...
 - 剑指offer:合并两个排序的链表
			
题目描述: 输入两个单调递增的链表,输出两个链表合成后的链表,当然我们需要合成后的链表满足单调不减规则. 解题思路: 这道题应该考察也是链表的相关操作.具体实现,新建一个新的链表,用两个指针分别指向两 ...
 - TAC队--团队选题报告
			
The Art of Code--团队选题报告 一个APP项目能否被大众所接受,能否拥有受众,the most important是它的idea. 一个好的idea可以为项目带来巨大的改变 一个 独特 ...