AcWing 241. 楼兰图腾
原题链接
简单
作者:
辰风
,
2020-03-04 10:32:17
,
所有人可见
,
阅读 761
思路
代码
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;
typedef long long LL;
const int N = 200010;
int n;
int a[N];
int tr[N];
int Greater[N], lower[N];
int lowbit(int x)
{
return x & -x;
}
void add(int x, int c)
{
for (int i = x; i <= n; i += lowbit(i)) tr[i] += c;
}
int sum(int x)
{
int res = 0;
for (int i = x; i; i -= lowbit(i)) res += tr[i];
return res;
}
int main()
{
scanf("%d", &n);
for (int i = 1; i <= n; i ++ ) scanf("%d", &a[i]);
for (int i = 1; i <= n; i ++ )
{
int y = a[i];
Greater[i] = sum(n) - sum(y);//求从左往右,比yi大的数有几个,比yi小的是有几个
lower[i] = sum(y - 1);
add(y, 1);
}
memset(tr, 0, sizeof tr);//一定要清空
LL res1 = 0, res2 = 0;
for (int i = n; i; i -- )//再从右往左来算一遍
{
int y = a[i];
res1 += Greater[i] * (LL)(sum(n) - sum(y));
res2 += lower[i] * (LL)(sum(y - 1));
add(y, 1);
}
printf("%lld %lld\n", res1, res2);
return 0;
}