Description

原题链接

给你一个长度为\(n\)的排列\(~P\),定义一段子区间是好的,当且仅当这个子区间内的值构成了连续的一段。例如对于排列\(\{1,3,2 \}\),\([1, 1], [2, 2], [3, 3], [2, 3], [1, 3]\)是好的区间。

共\(q\)次询问,每次询问\(L,R\), 求有多少\(L \leq l \leq r \leq R\),满足\([l, r]\)是好的区间。\(1 \leq n, q \leq 1.2 \times 10 ^ 5\).

Solution

可以发现,区间\([l, r]\)是好的,当且仅当\(~(Max_{i = l}^{r} - Min_{i = l} ^ {r}) - (r - l) = 0\).

考虑维护一段区间上式的最小值(以下的最小值都指上式最小值),每一个最小值为\(0\)的位置都可以和当前的\(r\)组成一个好的区间。不难发现,一个右端点能产生的贡献为它左边的点的最小值为\(0\)的个数,于是可以在线段树上维护最小值和最小值个数,以及每个最小值为\(0\)的位置产生的贡献。

由于右边新加的点会对已有的点产生影响,考虑离线询问,按右端点排序,用两个单调栈分别维护当前\(Min\)和\(Max\)。右端点右移时,势必会使整个区间的最小值减一,也势必会使其未右移前的右端点对答案产生一轮贡献,每次处理右端点等于当前枚举点的答案。时间复杂度\(O(n \log n)\).

Code

#include <bits/stdc++.h>

#define For(i, j, k) for (int i = j; i <= k; ++ i)
#define Forr(i, j, k) for (int i = j; i >= k; -- i) using namespace std; typedef long long ll; inline int read() {
int x = 0, p = 1; char c = getchar();
for (; !isdigit(c); c = getchar()) if (c == '-') p = -1;
for (; isdigit(c); c = getchar()) x = (x << 1) + (x << 3) + (c ^ 48);
return x * p;
} inline void File() {
freopen("CF997E.in", "r", stdin);
freopen("CF997E.out", "w", stdout);
} const int N = 1.2e5 + 10;
int n, q, a[N], s1[N], t1, s2[N], t2, tt = 1; ll ans[N]; struct Query {
int id, l, r;
bool operator < (const Query &rhs) const { return r < rhs.r; }
} Q[N]; namespace Segment_Tree {
#define lc (rt << 1)
#define rc (rt << 1 | 1)
#define mid (l + r >> 1) const int MAXN = N << 2;
int mn[MAXN], tag[MAXN], t[MAXN]; ll sum[MAXN], tg[MAXN]; inline void pushdown(int rt) {
if (tag[rt]) {
mn[lc] += tag[rt], mn[rc] += tag[rt];
tag[lc] += tag[rt], tag[rc] += tag[rt];
tag[rt] = 0;
} if (tg[rt]) {
if (mn[lc] == mn[rt]) sum[lc] += 1ll * t[lc] * tg[rt], tg[lc] += tg[rt];
if (mn[rc] == mn[rt]) sum[rc] += 1ll * t[rc] * tg[rt], tg[rc] += tg[rt];
tg[rt] = 0;
}
} inline void pushup(int rt) {
t[rt] = 0, mn[rt] = min(mn[lc], mn[rc]); t[rt] = mn[rt] == mn[lc] ? t[rt] + t[lc] : t[rt];
t[rt] = mn[rt] == mn[rc] ? t[rt] + t[rc] : t[rt]; sum[rt] = sum[lc] + sum[rc];
} inline void Build(int rt, int l, int r) {
mn[rt] = l, t[rt] = 1;
if (l ^ r) Build(lc, l, mid), Build(rc, mid + 1, r);
} inline void update(int rt, int l, int r, int L, int R, int v) {
if (L <= l && r <= R) { mn[rt] += v, tag[rt] += v; return ; }
pushdown(rt); if (L <= mid) update(lc, l, mid, L, R, v);
if (R > mid) update(rc, mid + 1, r, L, R, v); pushup(rt);
} inline ll query(int rt, int l, int r, int L, int R) {
if (L <= l && r <= R) return sum[rt]; pushdown(rt);
if (R <= mid) return query(lc, l, mid, L, R);
if (L > mid) return query(rc, mid + 1, r, L, R);
return query(lc, l, mid, L, R) + query(rc, mid + 1, r, L, R);
} #undef lc
#undef rc
#undef mid
} int main() {
File(); using namespace Segment_Tree; n = read(); For(i, 1, n) a[i] = read();
q = read(); For(i, 1, q) Q[i].l = read(), Q[i].r = read(), Q[i].id = i; sort(Q + 1, Q + 1 + q); Build(1, 1, n); For(nr, 1, n) { mn[1] -= 1, tag[1] -= 1; for (; t1 && a[s1[t1]] < a[nr]; -- t1)
update(1, 1, n, s1[t1 - 1] + 1, s1[t1], a[nr] - a[s1[t1]]);
s1[++ t1] = nr; for (; t2 && a[s2[t2]] > a[nr]; -- t2)
update(1, 1, n, s2[t2 - 1] + 1, s2[t2], a[s2[t2]] - a[nr]);
s2[++ t2] = nr; sum[1] += t[1], tg[1] += 1; for (; tt <= q && Q[tt].r == nr; ++ tt)
ans[Q[tt].id] = query(1, 1, n, Q[tt].l, nr);
} For(i, 1, q) printf("%lld\n", ans[i]); return 0;
}

【CF997E】Good Subsegments (线段树+单调栈)的更多相关文章

  1. Codeforces 781E Andryusha and Nervous Barriers 线段树 单调栈

    原文链接https://www.cnblogs.com/zhouzhendong/p/CF781E.html 题目传送门 - CF781E 题意 有一个矩形,宽为 w ,高为 h .一开始会有 w 个 ...

  2. 洛谷P4425 转盘 [HNOI/AHOI2018] 线段树+单调栈

    正解:线段树+单调栈 解题报告: 传送门! 1551又是一道灵巧连题意都麻油看懂的题,,,,所以先解释一下题意好了,,,, 给定一个n元环 可以从0时刻开始从任一位置出发 每次可以选择向前走一步或者在 ...

  3. 线段树+单调栈+前缀和--2019icpc南昌网络赛I

    线段树+单调栈+前缀和--2019icpc南昌网络赛I Alice has a magic array. She suggests that the value of a interval is eq ...

  4. 牛客多校第四场sequence C (线段树+单调栈)

    牛客多校第四场sequence C (线段树+单调栈) 传送门:https://ac.nowcoder.com/acm/contest/884/C 题意: 求一个$\max {1 \leq l \le ...

  5. Codeforces 1175F - The Number of Subpermutations(线段树+单调栈+双针/分治+启发式优化)

    Codeforces 题面传送门 & 洛谷题面传送门 由于这场的 G 是道毒瘤题,蒟蒻切不动就只好来把这场的 F 水掉了 看到这样的设问没人想到这道题吗?那我就来发篇线段树+单调栈的做法. 首 ...

  6. [Codeforces1132G]Greedy Subsequences——线段树+单调栈

    题目链接: Codeforces1132G 题目大意:给定一个序列$a$,定义它的最长贪心严格上升子序列为$b$满足若$a_{i}$在$b$中则$a_{i}$之后第一个比它大的也在$b$中.给出一个数 ...

  7. BZOJ.4540.[HNOI2016]序列(莫队/前缀和/线段树 单调栈 RMQ)

    BZOJ 洛谷 ST表的一二维顺序一定要改过来. 改了就rank1了哈哈哈哈.自带小常数没办法. \(Description\) 给定长为\(n\)的序列\(A_i\).\(q\)次询问,每次给定\( ...

  8. AtCoder Regular Contest 063 F : Snuke’s Coloring 2 (线段树 + 单调栈)

    题意 小 \(\mathrm{C}\) 很喜欢二维染色问题,这天他拿来了一个 \(w × h\) 的二维平面 , 初始时均为白色 . 然后他在上面设置了 \(n\) 个关键点 \((X_i , Y_i ...

  9. cdqz2017-test10-rehearsal(CDQ分治&可持久化线段树&单调栈)

    题意: 给出n个三元组 e[i]=(si,ti,wi) 第i个三元组的价值为 Σ w[j] ,j 满足以下4个条件: 1.j<i 2.tj<ti 3.sj<si 4.不存在j< ...

随机推荐

  1. 1171: lfx捧杯稳啦!

    escription Lfx在复习离散的时候突然想到了一个算法题,毕竟是lfx, 算法题如下: 他想知道这样的问题,先定义1~n中即是3的倍数,又是11的倍数的那些数的和sum, 他想知道sum有多少 ...

  2. python中map()函数用法

    map函数的原型是map(function, iterable, …),它的返回结果是一个列表. 参数function传的是一个函数名,可以是python内置的,也可以是自定义的. 参数iterabl ...

  3. vue echarts 动态数据

    安装echarts依赖 npm install echarts -S 或者使用国内的淘宝镜像: 安装 npm install -g cnpm --registry=https://registry.n ...

  4. httpd.conf简单配置

    本文介绍apache中httpd.conf的配置.该配置也可解决打开php文件却变成下载的尴尬情况 1 修改网站根目录查找DocumentRoot有这么一行DocumentRoot "C:/ ...

  5. MySQL 使用左连接替换not in

    众所周知,左连接和右连接的含义是以哪一张表为准. 左连接就是以左表为准,查出的结果中包含左表所有的记录,如果右表中没有与其对应的记录,那么那一行记录中B表部分的内容就全是NULL. 现在有两个表,一个 ...

  6. Golang中进行reslice时的注意事项

    先看下面代码: package main import "fmt" func main() { slice := []int{0, 1, 2, 3, 4, 5, 6, 7, 8} ...

  7. [翻译]在asp.net core2.0 OpenID Connect Handler中丢失了声明(CLaims)?

    注:这是一篇翻译,来自这里.这篇文章讲述了在asp.net core2.0中使用openid connect handler的过程中解析不到你想要的claim时,你可以参考这篇文章. Missing ...

  8. [转帖]cmd批处理常用符号详解

    cmd批处理常用符号详解 https://www.jb51.net/article/32866.htm 很多符号 还是不清楚的.. 批处理能够极大的提高 工作效率 需要加强深入学习.   1.@一般在 ...

  9. [转帖]Docker的数据管理(volume/bind mount/tmpfs)

    Docker(十五)-Docker的数据管理(volume/bind mount/tmpfs) https://www.cnblogs.com/zhuochong/p/10069719.html do ...

  10. Vue 鼠标移入移出事件

    Vue 中鼠标移入移出事件 @mouseover和@mouseleave 然后绑定style   现在开始代码示例 <template> <div class="pc&qu ...