1688 求逆序对
时间限制: 1 s
空间限制: 128000 KB
题目等级 : 黄金 Gold
题目描述 Description
给定一个序列a1,a2,…,an,如果存在i<j并且ai>aj,那么我们称之为逆序对,求逆序对的数目
数据范围:N<=105。Ai<=105。时间限制为1s。
输入描述 Input Description
第一行为n,表示序列长度,接下来的n行,第i+1行表示序列中的第i个数。
输出描述 Output Description
所有逆序对总数.
样例输入 Sample Input
4
3
2
3
2
样例输出 Sample Output
3
分析 Analysis
裸题,数据还水。
其实是我拿来练树状数组求逆序对的= =。
代码 Code
1 #include<cstdio> 2 #include<iostream> 3 #define maxn 1010101 4 #define lowbit(x) (-x&x) 5 using namespace std; 6 7 long long n,t[maxn],a[maxn],maxx = 0,tot; 8 9 void add(long long p){ 10 while(p <= maxx){ 11 t[p]++; 12 p += lowbit(p); 13 } 14 } 15 16 long long sum(long long p){ 17 long long ans = 0; 18 while(p){ 19 ans += t[p]; 20 p -= lowbit(p); 21 } 22 return ans; 23 } 24 25 int main(){ 26 scanf("%lld",&n); 27 for(int i = 1;i <= n;i++){ 28 scanf("%lld",&a[i]); 29 maxx = max(maxx,a[i]); 30 } 31 32 for(int i = n;i >= 1;i--){ 33 tot += sum(a[i]-1); 34 add(a[i]); 35 } 36 37 printf("%lld",tot); 38 39 return 0; 40 }