描述
逆序对:有 n 个数字,所有数字各不相同。假设第i个数字和第j个数字,i<j(1 ≤ i < j ≤ n),而且 a[i] > a[j],则 <a[i], a[j]> 称为a的一个逆序对。例如 存在5个数字,分别是:9 1 4 3 6 <9,1>是逆序对,9是第1个数字,1是第2个数字,9>1其他的逆序对同理。<9,4> <9,3> <9,6> <4,3>输入n个正整数,n<=10000,输入的每个数字[1,10000]
输入描述
两行,第一行一个整数n表示正整数的个数
第二行输入n个数
输出描述
每个数字对应的逆序对个数<例如 逆序对 (7,1) 算是属于7的逆序对>
样例输入 1
7 7 10 5 4 8 1 6
样例输出 1
4 5 2 1 2 0 0
#include<bits/stdc++.h>
using namespace std;
int n,ans=0;
int a[100010],c[100010],b[100010];
int lowbit(int x){
return x&(-x);
}
void update(int x,int y){
for(int i=x;i<=100000;i+=lowbit(i)){
c[i]+=y;
}
}
int sum(int x){
int s=0;
while(x>0){
s+=c[x];
x-=lowbit(x);
}
return s;
}
int main(){
cin>>n;
for(int i=1;i<=n;i++){
cin>>a[i];
}
for(int i=n;i>=1;i--){
int x=a[i];
b[i]=sum(x-1); //数字a[i]产生的逆序对数量
ans+=sum(x-1);
update(x,1);
}
for(int i=1;i<=n;i++){
cout<<b[i]<<" ";
}
cout<<endl<<ans;
return 0;
}
//a[]={6,1,8,4,5,10,7}
//
//a[i]=6;
//c[6]++; c[8]---c[16] c[x>100000] //统计6出现的次数
//1~5出现的次数就是和6组成的逆序对数量
//sum(6-1)=0
//
//a[i]=1;
//c[1]++;
//
//sum(7)=c7+c6+c4=2