题意

数轴上有 \(n\) 个点,每一次你可以将所有位置在 \(x\) 的点移动到 \(x-1\) 或者是移动到 \(x+1\),花费为 \(1\)。

有 \(q\) 次操作,每一次会在数轴上添加一个原来没有的点或者是删除一个原来已经有的点。在所有操作前和每一次操作后你需要回答将所有点集中到不超过两个点的最小花费。

\(\texttt{Data Range:}1\leq n,q\leq 10^5\)

前言

你打开了本题。

你发现是已经写过了 \(998244353\) 遍的维护最大的邻项之差。

你熟练的写出了代码,但是发现需要分类讨论,很头疼。

你翻开了题解,发现题解也是分类讨论。

相信经历了这么多的你心中满满的“我太难了”。

那么这篇题解将拯救你于水火之中(?)

题解

注意到肯定是左边一段的点放在一起右边一段的点放在一起。

假设当前一共有 \(n\) 个点,从小到大依次为 \(p_1,\cdots,p_n\),考虑让 \(p_1,\cdots,p_k\) 放在一起,\(p_{k+1},\cdots,p_n\) 放在一起,那么花费为 \(p_k-p_1+p_n-p_{k+1}=(p_n-p_1)-(p_{k+1}-p_k)\)。

注意到对于每一个加点删点的操作来说 \(p_n-p_1\) 很容易维护,然后 \(p_{k+1}-p_k\) 就是开个 multiset 维护最大差值就完了。

但是这东西需要分类讨论很麻烦,所以我们想个办法让维护这东西变得很轻松不需要分类讨论。

考虑 Splay 预处理的时候往里面加 \(\infty\) 和 \(-\infty\),所以我们也可以往里面加 \(\infty\) 和 \(-\infty\)。

然后询问的时候最大的两个绝对是 \(p_1-(-\infty)\) 和 \(\infty-p_n\),于是只需要查询第三大的那个就好了,没有第三大的答案就是 \(0\)。

这么写可以规避各种各样的分类讨论,比如说什么新插入的值没有前驱后继啦,什么插入点之前 multiset 里元素不够啦什么的,何乐而不为呢?

代码

#include<bits/stdc++.h>
using namespace std;
typedef long long int ll;
const ll MAXN=2e5+51,inf=1e15;
multiset<ll>st,gap;
multiset<ll>::iterator it;
ll n,qcnt,op,u,prv,nxt,mx,mn;
ll x[MAXN];
inline ll read()
{
register ll num=0,neg=1;
register char ch=getchar();
while(!isdigit(ch)&&ch!='-')
{
ch=getchar();
}
if(ch=='-')
{
neg=-1;
ch=getchar();
}
while(isdigit(ch))
{
num=(num<<3)+(num<<1)+(ch-'0');
ch=getchar();
}
return num*neg;
}
inline void erase(ll x)
{
gap.erase(gap.find(x));
}
inline ll query()
{
if(*gap.begin()>=1e12)
{
return 0;
}
it=st.begin(),mn=*(++it),it=st.end(),--it,mx=*(--it);
return it=gap.end(),--it,--it,mx-mn-*(--it);
}
int main()
{
n=read(),qcnt=read(),st.insert(inf),st.insert(-inf);
for(register int i=1;i<=n;i++)
{
st.insert(x[i]=read());
}
sort(x+1,x+n+1),x[0]=-inf,x[n+1]=inf;
for(register int i=1;i<=n+1;i++)
{
gap.insert(x[i]-x[i-1]);
}
printf("%lld\n",query());
for(register int i=0;i<qcnt;i++)
{
op=read(),u=read();
if(op==0)
{
it=st.find(u),prv=u-*(--it),it++,nxt=*(++it)-u;
st.erase(u),erase(prv),erase(nxt),gap.insert(nxt+prv);
}
if(op==1)
{
it=st.upper_bound(u),nxt=*(it--),prv=*it,st.insert(u);
erase(nxt-prv),gap.insert(nxt-u),gap.insert(u-prv);
}
if(*gap.begin()>=1e12)
{
puts("0");
continue;
}
printf("%lld\n",query());
}
}

CodeForces 1418D Trash Problem的更多相关文章

  1. codeforces 340C Tourist Problem

    link:http://codeforces.com/problemset/problem/340/C 开始一点也没思路,赛后看别人写的代码那么短,可是不知道怎么推出来的啊! 后来明白了. 首先考虑第 ...

  2. codeforces B. Routine Problem 解题报告

    题目链接:http://codeforces.com/problemset/problem/337/B 看到这个题目,觉得特别有意思,因为有熟悉的图片(看过的一部电影).接着让我很意外的是,在纸上比划 ...

  3. Codeforces 527D Clique Problem

    http://codeforces.com/problemset/problem/527/D 题意:给出一些点的xi和wi,当|xi−xj|≥wi+wj的时候,两点间存在一条边,找出一个最大的集合,集 ...

  4. Codeforces 706C - Hard problem - [DP]

    题目链接:https://codeforces.com/problemset/problem/706/C 题意: 给出 $n$ 个字符串,对于第 $i$ 个字符串,你可以选择花费 $c_i$ 来将它整 ...

  5. Codeforces 1096D - Easy Problem - [DP]

    题目链接:http://codeforces.com/problemset/problem/1096/D 题意: 给出一个小写字母组成的字符串,如果该字符串的某个子序列为 $hard$,就代表这个字符 ...

  6. Codeforces 793C - Mice problem(几何)

    题目链接:http://codeforces.com/problemset/problem/793/C 题目大意:给你一个捕鼠器坐标,和各个老鼠的的坐标以及相应坐标的移动速度,问你是否存在一个时间点可 ...

  7. CodeForces 687A NP-Hard Problem

    Portal:http://codeforces.com/problemset/problem/687/A 二分图染色 好模板题 有SPJ 值得注意的是,因为C++的奇妙的运算机制 若在vector变 ...

  8. Codeforces Gym 100342J Problem J. Triatrip 求三元环的数量 bitset

    Problem J. Triatrip Time Limit: 20 Sec Memory Limit: 256 MB 题目连接 http://codeforces.com/gym/100342/at ...

  9. Codeforces Gym 100342C Problem C. Painting Cottages 转化题意

    Problem C. Painting CottagesTime Limit: 2 Sec Memory Limit: 256 MB 题目连接 http://codeforces.com/gym/10 ...

随机推荐

  1. 【Java并发编程】面试常考的ThreadLocal,超详细源码学习

    目录 ThreadLocal是啥?用来干啥? ThreadLocal的简单使用 ThreadLocal的实现思路? ThreadLocal常见方法源码分析 ThreadLocal.set(T valu ...

  2. Spring Boot第四弹,一文教你如何无感知切换日志框架?

    持续原创输出,点击上方蓝字关注我吧 目录 前言 Spring Boot 版本 什么是日志门面? 如何做到无感知切换? 如何切换? 引入依赖 指定配置文件 日志如何配置? 总结 前言 首先要感谢一下读者 ...

  3. Centos-检查文件系统并尝试修复-fsck

    fsck 检查文件系统并尝试修改错误,修复对象为设备,本质上是调用 /sbin/fsck.filesystemName 命令, filesystemName是指定设备的文件系统类型,如图分区中有文件丢 ...

  4. gRPC-微服务间通信实践

    微服务间通信常见的两种方式 由于微服务架构慢慢被更多人使用后,迎面而来的问题是如何做好微服务间通信的方案.我们先分析下目前最常用的两种服务间通信方案. gRPC(rpc远程调用) 场景:A服务主动发起 ...

  5. Python numpy总结(3)——常用函数用法

    1,np.ceil(x, y) 限制元素范围,进一法,即向上取整. x 表示输入的数据  y float类型 表示每个元素的上限. a = np.array([-1.7, -1.5, -0.2, 0. ...

  6. 实验 6:OpenDaylight 实验——OpenDaylight 及 Postman 实现流表下发

    一.实验目的 熟悉 Postman 的使用;熟悉如何使用 OpenDaylight 通过 Postman 下发流表. 二.实验任务 流表有软超时和硬超时的概念,分别对应流表中的 idle_timeou ...

  7. 几个常用markdown工具的主要优缺点

    几个常用markdown工具的主要优缺点 最近对几个热门的markdown工具做了一个对比表 表格 脚注 图片和图床 平台 移动端 实时预览 收费 操作难度 导出功能 mweb 非常棒 预览正常显示 ...

  8. 带有Firebase的离子2:在OAuth 2中签名

    介绍 这是一个指南,展示如何在Android上使用Firebase认证谷歌用户. 背景 虽然很多人都写过这个指南,但是他们没有解释一个关键的部分--为什么在执行了每一步之后仍然会看到认证错误12501 ...

  9. 【Excel技巧】用IF函数进行等级评定

    如果下面给出一份"2月份语文成绩考核表",那么如何对成绩进行等级评定呢. 等级评定规则: 总分(100分) A级(91-100) B级(81-90) C级(71-80) D级(70 ...

  10. 多测师讲解IDE工具python_001.2pycham_安装

    PyCharm安装使用教程 Pycharm 是目前 Python 语言最好用的集成开发工具. 下载 Pycharm 载时有两种版本选择 Professional(专业版,收费)和Community(社 ...