题目链接

题目大意: 有一个博客, 初始分数为$0$, 有$n$个人, 第$i$个人有一个期望值$a_i$,

如果第$i$个人浏览博客时,博客赞数高于$a_i$博客分数$-1$, 低于$+1$, 相等不变,

对于每个$i$, 求出$[1,i]$的人按任意顺序浏览博客后最大分数.

题解:

首先, 用贪心可以知道所有人按期望升序排列, 最后得分一定最大

由于期望有负数, 博客分数一定是先减后增的, 然后对这两段分类讨论

对于递减的段, 最后分数为递增递减的临界值

假设临界值为$x$, 设比$x$小的数的个数为$cnt_x$

可以发现$x$是第一个满足 $cnt_x+x>=0$ 的$x$

比方说排序后序列为$-10,-10,-10,-6,-2,-1$ 那么$x$就为$-4$

权值线段树上二分即可求出$x$ (初值设为$x$, 转为二分第一个$>=0$的数)

在考虑递增区间, 假设当前一共有$r$个数

有转移方程 $f_i=min(a_i,f_{i-1}+1),$ $f$为得分, $a$为排序后数组

可以得到$f_r=min(a_r,a_{r-1}+1,a_{r-2}+2,...,a_{l}+r-l,x+(r-x))$, $a_{l}$为第一个比$x$大的数

用权值线段树维护最小值即可

 #include <iostream>
#include <algorithm>
#include <cstdio>
#define REP(i,a,n) for(int i=a;i<=n;++i)
#define mid ((l+r)>>1)
#define lc (o<<1)
#define rc (lc|1)
#define ls lc,l,mid
#define rs rc,mid+1,r
using namespace std; const int N = 5e5+, INF = 0x3f3f3f3f; int n, m, ans;
struct _ {
int mx,tag;
void upd(int x) {
mx+=x,tag+=x;
}
} v1[N<<], v2[N<<]; //v1维护的递减区间
//v2维护递增区间 void pd(_ *v, int o) {
if (v[o].tag) {
v[lc].upd(v[o].tag);
v[rc].upd(v[o].tag);
v[o].tag=;
}
} void add1(int o, int l, int r, int ql, int qr) {
if (ql<=l&&r<=qr) return v1[o].upd();
pd(v1,o);
if (mid>=ql) add1(ls,ql,qr);
if (mid<qr) add1(rs,ql,qr);
v1[o].mx=max(v1[lc].mx,v1[rc].mx);
} void add2(int o, int l, int r, int ql, int qr) {
if (ql<=l&&r<=qr) return v2[o].upd();
pd(v2,o);
if (mid>=ql) add2(ls,ql,qr);
if (mid<qr) add2(rs,ql,qr);
v2[o].mx=min(v2[lc].mx,v2[rc].mx);
} int qry1(int o, int l, int r) {
if (l==r) return l;
pd(v1,o);
if (v1[lc].mx>=) return qry1(ls);
return qry1(rs);
} void qry2(int o, int l, int r, int ql, int qr) {
if (v2[o].mx>=ans) return;
if (ql<=l&&r<=qr) return ans=min(ans,v2[o].mx),void();
pd(v2,o);
if (mid>=ql) qry2(ls,ql,qr);
if (mid<qr) qry2(rs,ql,qr);
} void build1(int o, int l, int r) {
if (l==r) return v1[o].mx=l,void();
build1(ls),build1(rs);
v1[o].mx=max(v1[lc].mx,v1[rc].mx);
} void build2(int o, int l, int r) {
if (l==r) return v2[o].mx=l,void();
build2(ls),build2(rs);
v2[o].mx=min(v2[lc].mx,v2[rc].mx);
} int main() {
scanf("%d", &n);
build1(,-N,);
build2(,-N,N);
REP(i,,n) {
int k;
scanf("%d", &k);
if (k<) add1(,-N,,k,N);
add2(,-N,N,-N,k-);
int x = qry1(,-N,);
ans = INF, qry2(,-N,N,x,N);
printf("%d\n", ans);
}
}

Blog Post Rating CodeForces - 806E (线段树二分)的更多相关文章

  1. Bash and a Tough Math Puzzle CodeForces - 914D (线段树二分)

    大意:给定序列, 单点修改, 区间询问$[l,r]$内修改至多一个数后$gcd$能否为$x$ 这题比较有意思了, 要注意到询问等价于$[l,r]$内最多有1个数不为$x$的倍数 可以用线段树维护gcd ...

  2. Nastya and King-Shamans CodeForces - 992E (线段树二分)

    大意: 给定序列a, 单点更新, 询问是否存在a[i]等于s[i-1], s为a的前缀和, a非负 考虑到前缀和的单调性, 枚举从1开始前缀和, 找到第一个大于等于s[1]的a[i], 如果相等直接输 ...

  3. Codeforces Gym 100803G Flipping Parentheses 线段树+二分

    Flipping Parentheses 题目连接: http://codeforces.com/gym/100803/attachments Description A string consist ...

  4. Codeforces Gym 100231B Intervals 线段树+二分+贪心

    Intervals 题目连接: http://codeforces.com/gym/100231/attachments Description 给你n个区间,告诉你每个区间内都有ci个数 然后你需要 ...

  5. Educational Codeforces Round 64 (Rated for Div. 2) (线段树二分)

    题目:http://codeforces.com/contest/1156/problem/E 题意:给你1-n  n个数,然后求有多少个区间[l,r] 满足    a[l]+a[r]=max([l, ...

  6. hdu4614 线段树+二分 插花

    Alice is so popular that she can receive many flowers everyday. She has N vases numbered from 0 to N ...

  7. 洛谷P4344 脑洞治疗仪 [SHOI2015] 线段树+二分答案/分块

    !!!一道巨恶心的数据结构题,做完当场爆炸:) 首先,如果你用位运算的时候不小心<<打成>>了,你就可以像我一样陷入疯狂的死循环改半个小时 然后,如果你改出来之后忘记把陷入死循 ...

  8. luogu4422 [COCI2017-2018#1] Deda[线段树二分]

    讨论帖:线段树二分的题..我还考场切过..白学 这题我一年前的模拟赛考场还切过,现在就不会了..好菜啊. 显然直接线段树拆成$\log n$个区间,然后每个区间在进行线段树二分即可. UPD:复杂度分 ...

  9. Bash and a Tough Math Puzzle CodeForces 914D 线段树+gcd数论

    Bash and a Tough Math Puzzle CodeForces 914D 线段树+gcd数论 题意 给你一段数,然后小明去猜某一区间内的gcd,这里不一定是准确值,如果在这个区间内改变 ...

随机推荐

  1. quartz-job实现实时或定时发送短信任务

    存放调度器(Job 和 Trigger)信息的xml配置文件: 这是某个指定的要实现的定时任务: <!-- 每天给项目经理发送短信避免短信服务挂了 定时每天08:30执行--> <j ...

  2. Python之路----内置函数补充与匿名函数

    内置函数补充:reversed()保留原列表,返回一个反向的迭代器 l = [1,2,3,4,5] l.reverse() print(l) l = [1,2,3,4,5] l2 = reversed ...

  3. SQL语句调优汇总

    1.插入数据的表或临时表,预先创建好表结构,能够加快执行速度 2.where 条件判断的字段以及连接查询的条件字段   都添加上索引   能够加快执行速度 3.尽量避免使用 like ,类似 like ...

  4. LOJ10066 新的开始

    LOJ10066 新的开始 prim 典型题.碰到这种情况,只要建一个虚拟节点,和其他的点连边,按题目给权值即可 代码中把n+1当成虚拟节点 懒得写kruskal就用prim了 #include< ...

  5. JDBC批量插入数据优化,使用addBatch和executeBatch

    JDBC批量插入数据优化,使用addBatch和executeBatch SQL的批量插入的问题,如果来个for循环,执行上万次,肯定会很慢,那么,如何去优化呢? 解决方案:用 preparedSta ...

  6. 20145227鄢曼君《网络对抗》shellcode注入&Return-to-libc攻击深入

    20145227鄢曼君<网络对抗>shellcode注入&Return-to-libc攻击深入 shellcode注入实践 shellcode基础知识 Shellcode实际是一段 ...

  7. android 实践项目 总结 (修改)

    Android手机定位与地图实现 在一个不熟悉的环境中,获得自己的位置,选择合适的就餐地点,住宿和公交路线成为一项难题.本次的实践项目就是为了解决上述难题的,通过调用百度地图的接口实现定位.查询公交路 ...

  8. 再谈vim中多窗口的编辑 ctrl+w+H窗口位置最大化和互换等操作

    参考:http://blog.csdn.net/shuangde800/article/details/11430659 很好 鼠标在各个窗口间循环移动: ctrl+w+(小写的 hjkl), &qu ...

  9. 安卓开发 Activity入门

    生命周期 Activity包含5种状态,涉及7种方法 1. 启动状态 2. 运行状态 *** 即使内存不足,Android先销毁栈底的Activity,来确保当前Activity正常运行 3. 暂停状 ...

  10. LOJ #10222. 「一本通 6.5 例 4」佳佳的 Fibonacci

    题目链接 题目大意 $$F[i]=F[i-1]+F[i-2]\ (\ F[1]=1\ ,\ F[2]=1\ )$$ $$T[i]=F[1]+2F[2]+3F[3]+...+nF[n]$$ 求$T[n] ...