树状数组求逆序数

旋转序列求逆序数

#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int maxn=100010;
int n,a[maxn],b[maxn],c[maxn*2];
long long ans,res;
int low(int x){
    return x&(-x);
}
int add(int k){
    while(k){
        c[k]++;
        k-=low(k);
    }
} 
int sum(int k){
    int t=0;
    while(k<=n){
        t+=c[k];
        k+=low(k);
    }
    return t;
}
int main(){
    int T,i;
    scanf("%d",&T);
    while(T--){
        scanf("%d",&n);
        for(i=1;i<=n;i++){
            scanf("%d",&a[i]);
            b[a[i]]=i;
        }
        ans=1e10;
        memset(c,0,sizeof(c));
        res=0;
        for(i=1;i<=n;i++){
            res+=sum(a[i]);
            add(a[i]);
        }
        ans=min(ans,res);
        //printf("%lld
",res);
        for(int i=1;i<=n;i++){
            int t=b[i];
            res-=(t-1);
            res+=(n-t);
            ans=min(ans,res);
        }
        printf("%lld
",ans);
    }
}
原文地址:https://www.cnblogs.com/ccsu-zry/p/9773436.html