BZOJ1150 [CTSC2007] 数据备份Backup 贪心_堆_神题
Description

非常神的一道题.
据说是模拟费用流(你也可以说是贪心加堆)
考虑最朴素的贪心:将所有元素都塞进一个堆里,那完一个就给旁边的打上标记,以此反复迭代.
不过,不难证明这种方法是完全错误的.
原因很简单:这个方法不能反悔,即每一个决策都是永久性的。
我们希望由可以反悔的机会。
首先,我们可以得到一个结论:
假若 $arr[i]$ 为当前数列中最小值,那么,如果不选 $arr[i]$,则一定要选择 $arr[i-1]$ 与 $arr[i+1]$。
于是,在加入 $arr[i]$,将其累积到答案中,并标记 $arr[i-1]$ 与 $arr[i+1]$ 不能选后,我们再将 $i$ 覆盖为 $arr[i-1]+arr[i+1]-arr[i]$。
为什么这样处理呢?
$arr[i]+arr[i-1]+arr[i+1]-arr[i]$ = $arr[i+1]+arr[i-1]$。以此达到了一个不断决策并反悔的过程。
以后可以专门学习一下模拟费用流,应该会对该问题有一个更加深刻的认识。
Code:
#include<bits/stdc++.h>
#define setIO(s) freopen(s".in","r",stdin)
#define maxn 1000000
#define inf 100000000000
using namespace std;
struct Node{
long long key;
int id;
Node(long long a=0,int b=0):key(a),id(b){}
bool operator < ( Node c) const{
return key > c.key;
}
};
priority_queue<Node>Q;
int tag[maxn],suf[maxn],pre[maxn];
long long h[maxn],arr[maxn];
int main(){
// setIO("input");
int n,k;
scanf("%d%d",&n,&k);
for(int i=1;i<=n;++i) scanf("%lld",&arr[i]);
for(int i=1;i<=n;++i) { h[i]=(long long) arr[i]-arr[i-1], suf[i]=i+1,pre[i]=i-1; }
h[0]=inf, suf[n]=pre[2]=0;
for(int i=2;i<=n;++i) Q.push(Node(h[i],i));
long long ans = 0;
for(int i=1;i<=k;++i) {
while(tag[Q.top().id]) Q.pop();
Node u = Q.top();
ans += (long long) u.key;
int cur = u.id;
int l = pre[cur],r = suf[cur];
h[cur] = h[l]+h[r]-h[cur];
tag[l]=tag[r]=1;
h[l]=h[r]=inf;
pre[cur]=pre[l],suf[pre[cur]] = cur;
suf[cur]=suf[r],pre[suf[r]] = cur;
Q.pop();
Q.push(Node(h[cur],cur));
}
printf("%lld",ans);
return 0;
}
BZOJ1150 [CTSC2007] 数据备份Backup 贪心_堆_神题的更多相关文章
- BZOJ1150 [CTSC2007]数据备份Backup 链表+小根堆
BZOJ1150 [CTSC2007]数据备份Backup 题意: 给定一个长度为\(n\)的数组,要求选\(k\)个数且两两不相邻,问最小值是多少 题解: 做一个小根堆,把所有值放进去,当选择一个值 ...
- BZOJ1150 [CTSC2007]数据备份Backup 贪心 堆
欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目传送门 - BZOJ1150 题意概括 数轴上面有一堆数字. 取出两个数字的代价是他们的距离. 现在要取出k对数,(一个数 ...
- bzoj1150 [CTSC2007]数据备份Backup 双向链表+堆
[CTSC2007]数据备份Backup Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 2727 Solved: 1099[Submit][Stat ...
- BZOJ1150 [CTSC2007]数据备份Backup 【堆 + 链表】
题目 你在一家 IT 公司为大型写字楼或办公楼(offices)的计算机数据做备份.然而数据备份的工作是枯燥乏味 的,因此你想设计一个系统让不同的办公楼彼此之间互相备份,而你则坐在家中尽享计算机游戏的 ...
- BZOJ1150[CTSC2007]数据备份Backup——模拟费用流+堆+链表
题目描述 你在一家 IT 公司为大型写字楼或办公楼(offices)的计算机数据做备份.然而数据备份的工作是枯燥乏味 的,因此你想设计一个系统让不同的办公楼彼此之间互相备份,而你则坐在家中尽享计算机游 ...
- bzoj1150: [CTSC2007]数据备份Backup
题目大意: 在n个点中,选出k对相邻的互不相同的点,使k段距离的总和最小. 贪心,双向链表. 首先,点之间的距离是动态的,所以要用堆来维护. 每次都选择最近的点.但因为其他情况,可能最终不会选择这 ...
- bzoj 1150: [CTSC2007]数据备份Backup【链表+堆】
参考:http://blog.csdn.net/Regina8023/article/details/44158947 神奇的做法.题意相当于若干个数取不相邻的k个使最小.先把数组差分,len表示这段 ...
- 【BZOJ1150】[CTSC2007]数据备份Backup 双向链表+堆(模拟费用流)
[BZOJ1150][CTSC2007]数据备份Backup Description 你在一家 IT 公司为大型写字楼或办公楼(offices)的计算机数据做备份.然而数据备份的工作是枯燥乏味的,因此 ...
- 【BZOJ 1150】 1150: [CTSC2007]数据备份Backup (贪心+优先队列+双向链表)
1150: [CTSC2007]数据备份Backup Description 你在一家 IT 公司为大型写字楼或办公楼(offices)的计算机数据做备份.然而数据备份的工作是枯燥乏味 的,因此你想设 ...
随机推荐
- Windows 环境下使用 GCC
安装 1.下载 min-gw 安装程序,链接为:http://sourceforge.net/projects/mingw/files/,下载 Download mingw-get-setup.exe ...
- MYSQL(一) 简单语法
MYSQL(一) 简单语法 1.默认约束:mysql里面DEFAULT关键字后面是不用加括号的 --1.1 创建数据库 mysql> create database holly; Query O ...
- BABEL转码解惑
众所周知,解决Nodejs异步问题的终极方案就是使用async/await方案,但是每次在项目中配置都会或多或少有些问题,每次都会被几个组件 babel-core babel-polyfill bab ...
- Nginx学习总结(2)——Nginx手机版和PC电脑版网站配置
考虑到网站的在多种设备下的兼容性,有很多网站会有手机版和电脑版两个版本.访问同一个网站URL,当服务端识别出用户使用电脑访问,就打开电脑版的页面,用户如果使用手机访问,则会得到手机版的页面. 1.判断 ...
- (21)Spring Boot过滤器、监听器【从零开始学Spring Boot】
Spring Boot 系列博客] )前言[从零开始学Spring Boot] : http://412887952-qq-com.iteye.com/blog/2291496 )spring boo ...
- (19)Spring Boot 添加JSP支持【从零开始学Spring Boot】
[来也匆匆,去也匆匆,在此留下您的脚印吧,转发点赞评论: 您的认可是我最大的动力,感谢您的支持] 看完本文章您可能会有些疑问,可以查看之后的一篇博客: 81. Spring Boot集成JSP疑问[从 ...
- mysql的用户访问权限规划
看了mysql的关于用户权限和安全的管理,感觉看起来还是不太好理解,首先mysql的连接方式是需要核对三个要素:user.passwd. host.而且这个user和passwd并不是o上面的user ...
- ubuntu-kill命令-杀死进程
显示进程pid ps -A 杀进程的命令 kill -s 9 xxx(进程pid)
- xtrabackup增量备份mysql +MHA
http://blog.csdn.net/yanggd1987/article/category/2214421 https://www.centos.bz/2013/09/innobackupex- ...
- caffe Solve函数
下面来看Solver<Dtype>::Solve(const char* resume_file) solver.cpp template <typename Dtype> v ...