题目链接 \(Click\) \(Here\)

这个题有点卡常数。。我的常数比较大所以是吸着氧气跑过去的。。。

题意:计算对于序列中每个位置\(p\),\([1,p-1]\)区间内比它大的数的个数,和\([p + 1, N]\)区间内比它小的数的个数和,要求支持修改操作,带修主席树可以解决。

通过主席树来维护权值状态和比某个数大/小的数的个数,用树状数组来支持修改和维护一个主席树的前缀和(主席树前缀和具有可减性)。时间空间\(O(Nlog^2N)\),\(1000ms+128MB\)的限制对本算法略为苛刻,但卡常可过。

#include <bits/stdc++.h>
using namespace std; const int N = 100010;
#define mid ((l + r) >> 1)
#define lowbit(x) (x & -x) int n, m, tot, rt[N], arr[N], pos[N]; struct Segment_Node {
int sz, ls, rs;
}t[N << 8]; void modify (int &_rt, int l, int r, int w, int del) {
if (_rt == 0) _rt = ++tot;
t[_rt].sz += del;
if (l != r) {
if (w <= mid) {
modify (t[_rt].ls, l, mid, w, del);
} else {
modify (t[_rt].rs, mid + 1, r, w, del);
}
}
} namespace rev {
int a[N]; inline void add (int pos, int val) {
while (pos <= n) {
a[pos] += val;
pos += lowbit (pos);
}
} inline int get_sum (int pos) {
register int res = 0;
while (pos) {
res += a[pos];
pos -= lowbit (pos);
}
return res;
} long long get_rev () {
long long res = 0;
for (int i = n; i >= 1;--i) {
res += get_sum (arr[i]);
add (arr[i], 1);
}
return res;
}
} int _query (int _rt, int l, int r, int nl, int nr) {
if (nl <= l && r <= nr) return t[_rt].sz;
register int res = 0;
if (nl <= mid) res += _query (t[_rt].ls, l, mid, nl, nr);
if (mid < nr) res += _query (t[_rt].rs, mid + 1, r, nl, nr);
return res;
} inline int query (int l, int r, int w, int type) {
l = l - 1;
//求序列里面[l, r]内有多少数大于w (type = 1)
//求序列里面[l, r]内有多少数小于w (type = 2)
// printf ("l = %d, r = %d, w = %d, type = %d\n", l, r, w, type);
register int i, res = 0;
for (i = l; i != 0; i -= lowbit (i)) {
if (type == 1) res -= _query (rt[i], 0, n + 1, w + 1, n);
if (type == 2) res -= _query (rt[i], 0, n + 1, 1, w - 1);
}
// printf ("res = %d\n", res);
for (i = r; i != 0; i -= lowbit (i)) {
if (type == 1) res += _query (rt[i], 0, n + 1, w + 1, n);
if (type == 2) res += _query (rt[i], 0, n + 1, 1, w - 1);
}
// printf ("l = %d, r = %d, w = %d, type = %d, res = %d\n", l, r, w, type, res);
return res;
} inline int read () {
int s = 0, w = 1, ch = getchar ();
while ('9' < ch || ch < '0') {
ch = getchar ();
}
while ('0' <= ch && ch <= '9') {
s = s * 10 + ch - '0';
ch = getchar ();
}
return s * w;
} int main () {
n = read (), m = read ();
register int i, j, w;
for (i = 1; i <= n; ++i) {
arr[i] = read ();
pos[arr[i]] = i;
for (j = i; j <= n; j += lowbit (j)) {
modify (rt[j], 0, n + 1, arr[i], +1);
}
}
long long ans = rev :: get_rev ();
for (i = 1, w = 0; i <= m; ++i) {
printf ("%lld\n", ans);
w = read ();
ans -= query (1, pos[w] - 1, w, 1);
ans -= query (pos[w] + 1, n, w, 2);
for (j = pos[w]; j <= n; j += lowbit (j)) {
modify (rt[j], 0, n + 1, w, -1);
}
}
}

Luogu P3157 [CQOI2011]动态逆序对的更多相关文章

  1. [Luogu P3157][CQOI2011]动态逆序对 (树套树)

    题面 传送门:[CQOI2011]动态逆序对 Solution 一开始我看到pty巨神写这套题的时候,第一眼还以为是个SB题:这不直接开倒车线段树统计就完成了吗? 然后冷静思考了一分钟,猛然发现单纯的 ...

  2. luogu P3157 [CQOI2011]动态逆序对(CDQ分治)

    题目描述 对于序列A,它的逆序对数定义为满足i<j,且Ai>Aj的数对(i,j)的个数.给1到n的一个排列,按照某种顺序依次删除m个元素,你的任务是在每次删除一个元素之前统计整个序列的逆序 ...

  3. LUOGU P3157 [CQOI2011]动态逆序对(CDQ 分治)

    传送门 解题思路 cdq分治,将位置看做一维,修改时间看做一维,权值看做一维,然后就转化成了三维偏序,用排序+cdq+树状数组.注意算删除贡献时要做两次cdq,分别算对前面和后面的贡献. #inclu ...

  4. P3157 [CQOI2011]动态逆序对

    P3157 [CQOI2011]动态逆序对 https://www.luogu.org/problemnew/show/P3157 题目描述 对于序列A,它的逆序对数定义为满足i<j,且Ai&g ...

  5. P3157 [CQOI2011]动态逆序对(树状数组套线段树)

    P3157 [CQOI2011]动态逆序对 树状数组套线段树 静态逆序对咋做?树状数组(别管归并QWQ) 然鹅动态的咋做? 我们考虑每次删除一个元素. 减去的就是与这个元素有关的逆序对数,介个可以预处 ...

  6. 洛谷 P3157 [CQOI2011]动态逆序对 解题报告

    P3157 [CQOI2011]动态逆序对 题目描述 对于序列\(A\),它的逆序对数定义为满足\(i<j\),且\(A_i>A_j\)的数对\((i,j)\)的个数.给\(1\)到\(n ...

  7. P3157 [CQOI2011]动态逆序对 (CDQ解决三维偏序问题)

    P3157 [CQOI2011]动态逆序对 题目描述 对于序列A,它的逆序对数定义为满足i<j,且Ai>Aj的数对(i,j)的个数.给1到n的一个排列,按照某种顺序依次删除m个元素,你的任 ...

  8. [BZOJ 3295] [luogu 3157] [CQOI2011]动态逆序对(树状数组套权值线段树)

    [BZOJ 3295] [luogu 3157] [CQOI2011] 动态逆序对 (树状数组套权值线段树) 题面 给出一个长度为n的排列,每次操作删除一个数,求每次操作前排列逆序对的个数 分析 每次 ...

  9. 洛谷 P3157 [CQOI2011]动态逆序对(树套树)

    题面 luogu 题解 树套树(树状数组套动态开点线段树) 静态使用树状数组求逆序对就不多说了 用线段树代替树状数组,外面套树状数组统计每个点逆序对数量 设 \(t1[i]\)为\(i\)前面有多少个 ...

随机推荐

  1. .NET提供了三种后台输出js的方式:

    .NET提供了三种后台输出js的方式: 首先创建 js文件testjs.js {    Page.ClientScript.RegisterClientScriptInclude("keys ...

  2. 配置 BizTalk Server

    使用“基本配置”或“自定义配置”配置 BizTalk Server. 基本配置与自定义配置       如果配置使用域组,则进行“自定义配置”. 如果配置使用自定义组名称而不是默认组名称,则进行“自定 ...

  3. codevs2822

    解题思路: tarjan缩点后算出度为0的点有几个,如果只有一个且这个点为爱心天使就行了: #include<iostream> #include<algorithm> #in ...

  4. fpm 打包教程

    常用yum命令: Yum安装时需要安装到指定的文件夹,则需要 --installroot yum install --installroot=/usr/src/ vim 常用rpm命令: 常用yum仓 ...

  5. BZOJ4475[Jsoi2015]子集选取——递推(结论题)

    题目描述 输入 输入包含一行两个整数N和K,1<=N,K<=10^9 输出 一行一个整数,表示不同方案数目模1,000,000,007的值. 样例输入 2 2 样例输出 16   可以发现 ...

  6. Docker镜像的使用

    当运行容器时,使用的镜像如果在本地中不存在,docker 就会自动从 docker 镜像仓库中下载,默认是从 Docker Hub 公共镜像源下载. 下面我们来学习: 1.管理和使用本地 Docker ...

  7. IDEA添加配置文件到classpath

    突然发现有一种简单的办法: IDEA 的 Mark Directory as 右键项目中的一个文件夹,会出现目录[Mark Directory as]选择[Resources Root] 实现下面原文 ...

  8. SSL加速卡调研的原因及背景

    SSL加速卡调研的原因及背景 SSL加速卡调研的原因及背景 网络信息安全已经成为电子商务和网络信息业发展的一个瓶颈,安全套接层(SSL)协议能较好地解决安全处理问题,而SSL加速器有效地提高了网络安全 ...

  9. jquery-Ajax请求用例码

    $.ajax({                    type:"post",                    url: 'domain’,                 ...

  10. 1286 unknown storage engine innodb

    打开my.ini  找到  loose-skip-innodb  与  skip-innodb  前面加上 #  注释掉,重启mysql 服务