求冒泡排序的交换次数即求逆序对数。
按照正常的求逆序对的方法和莫队方法添加删除即可。
注意不要把每次的ans清零。
#include <cmath>
#include <bitset>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
#define db double
#define sg string
#define rel(i,x,y) for(int i=(x);i<(y);i++)
#define rep(i,x,y) for(int i=(x);i<=(y);i++)
#define red(i,x,y) for(int i=(x);i>=(y);i--)
#define res(i,x) for(int i=head[x];i;i=nxt[i])
using namespace std;
const int N=1e5+5;
const int Inf=1e18;
const db Eps=1e-10;
int n,m,ans,a[N],bit[N];
#define lowbit(x) (x&(-x))
inline int read() {
int x=0;char ch=getchar();bool f=0;
while(ch>'9'||ch<'0'){if(ch=='-')f=1;ch=getchar();}
while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+ch-'0';ch=getchar();}
return f?-x:x;
}
void update(int x,int k) {
while(x<=n) bit[x]+=k,x+=lowbit(x);
}
int getsum(int x) {
int ret=0;while(x) ret+=bit[x],x-=lowbit(x);return ret;
}
int main() {
n=read();
rep(i,1,n) a[i]=read();
m=read();
int l=1,r=0;
while(m--) {
int x=read(),y=read();
while(r>y) {
update(a[r],-1);ans-=getsum(n)-getsum(a[r]-1);r--;
}
while(r<y) {
r++;ans+=getsum(n)-getsum(a[r]-1);update(a[r],1);
}
while(l<x) {
update(a[l],-1);ans-=getsum(a[l]-1);l++;
}
while(l>x) {
l--;ans+=getsum(a[l]-1);update(a[l],1);
}
printf("%d\n",ans);
}
return 0;
}