CF1042D Petya and Array 题解

比较典的一个题。

经验题:P2717 P5459

题意:给定 $\{a_n\},t$,求 $\sum\limits_{l=1}^n\sum\limits_{r=l}^n[\sum\limits_{i=l}^ra_i<t]$。

思路

令 $s_x=\sum\limits_{i=1}^xa_i$,则原式等于 $\sum\limits_{l=1}^n\sum\limits_{r=l}^n[s_r-s_{l-1}<t]$。

考虑枚举 $r$,统计 $l-1<r\bigwedge s_{l-1}>s_r-t$ 的 $l-1$ 的个数。

发现是个二维偏序,用权值树状数组维护之,复杂度 $O(n\log n)$。

代码

#include <cstdio>
#include <cctype>
#include <algorithm>
#define F(x) v[m++] = x
#define H(x) lower_bound(v, v + m, x) - v + 1
using namespace std;
inline long long R()
{
    long long r = 0;bool b = 0;char c = getchar();
    while(!isdigit(c)) b = c == '-', c = getchar();
    while(isdigit(c)) r = r * 10 + c - '0', c = getchar();
    return b ? -r : r;
}
int n, m = 1, c[400050];long long t, q, a[200050], v[400050];
void C(int x) {for(;x <= m;x += x & -x) ++c[x];}
int Q(int x)
{
    int q = 0, y = m;for(--x;y > x;y &= y - 1) q += c[y];
    for(;x > y;x &= x - 1) q -= c[x];return q;
}
int main()
{
    n = R();t = R();for(int i = 1;i <= n;++i)
    F(a[i] = a[i - 1] + R()), F(a[i] - t + 1);
    sort(v, v + m);m = unique(v, v + m) - v;C(H(0));
    for(int i = 1;i <= n;++i) q += Q(H(a[i] - t + 1)), C(H(a[i]));
    return printf("%lld", q), 0;
}
posted @ 2022-09-14 17:16  5k_sync_closer  阅读(4)  评论(0编辑  收藏  举报  来源