记录编号 364646 评测结果 AAAAAAAAAAAAAAAAAAAA
题目名称 [国家集训队2011]排队(魏铭) 最终得分 100
用户昵称 Gravatarliu_runda 是否通过 通过
代码语言 C++ 运行时间 1.151 s
提交时间 2017-01-17 16:07:08 内存使用 27.31 MiB
显示代码纯文本
#include<cstdio>
#include<cstdlib>
#include<algorithm>
using namespace std;
const int maxn=20005;
struct node{
  node *ch[2];
  int data,Min,Max,ord,sz;
  node(int x){
    Min=Max=data=x;ord=rand();sz=1;ch[0]=ch[1]=0;
  }
  node(){}
  void update(){
    Min=Max=data;sz=1;
    if(ch[0])sz+=ch[0]->sz,Min=min(Min,ch[0]->Min),Max=max(Max,ch[0]->Max);
    if(ch[1])sz+=ch[1]->sz,Min=min(Min,ch[1]->Min),Max=max(Max,ch[1]->Max);
  }
}t[maxn*50];int tot=0;
node* newnode(int x){
  t[++tot]=node(x);return t+tot;
}
void rot(node* &rt,int t){
  node *c=rt->ch[t];rt->ch[t]=c->ch[t^1];c->ch[t^1]=rt;rt=c;
  rt->ch[t^1]->update();rt->update();
}
void insert(node* &rt,int x){
  if(!rt){
    rt=newnode(x);return;
  }
  int t=(x>=rt->data);
  insert(rt->ch[t],x);
  rt->update();
  if(rt->ch[t]->ord>rt->ord)rot(rt,t);
}
void remove(node* &rt,int x){
  if(x==rt->data){
    if(!rt->ch[0])rt=rt->ch[1];
    else if(!rt->ch[1])rt=rt->ch[0];
    else{
      int t=(rt->ch[0]->ord<rt->ch[1]->ord);
      rot(rt,t);remove(rt->ch[t^1],x);rt->update();
    }
  }else{
    remove(rt->ch[x>rt->data],x);
    rt->update();
  }
}
int getsz(node *rt){
  return rt?rt->sz:0;
}
int rk(node *rt,int x){//how many numbers smaller than x
  if(!rt)return 0;
  if(x<=rt->data)return rk(rt->ch[0],x);
  return getsz(rt->ch[0])+1+rk(rt->ch[1],x);
}
int RK(node *rt,int x){//how many numbers larger than x
  if(!rt)return 0;
  if(x>=rt->data)return RK(rt->ch[1],x);
  return getsz(rt->ch[1])+1+RK(rt->ch[0],x);
}
int n,m;
int a[maxn];
node* BIT[maxn];
inline int lowbit(int x){return x&(-x);}
void build(){
  for(int i=1;i<=n;++i){
    for(int j=i;j<=n;j+=lowbit(j)){
      insert(BIT[j],a[i]);
    }
  }
}
int Qsmall(int x,int w){
  int ans=0;
  for(;x;x-=lowbit(x))ans+=rk(BIT[x],w);
  return ans;
}
int Qsmall(int l,int r,int w){
  return Qsmall(r,w)-Qsmall(l-1,w);
}
int Qlarge(int x,int w){
  int ans=0;
  for(;x;x-=lowbit(x))ans+=RK(BIT[x],w);
  return ans;
}
int Qlarge(int l,int r,int w){
  return Qlarge(r,w)-Qlarge(l-1,w);
}
void Insert(int x,int w){
  for(;x<=n;x+=lowbit(x))insert(BIT[x],w);
}
void Remove(int x,int w){
  for(;x<=n;x+=lowbit(x))remove(BIT[x],w);
}
int c[maxn];
void add(int x){
  for(;x;x-=lowbit(x))c[x]++;
}
int sum(int x){
  int ans=0;
  for(;x<maxn;x+=lowbit(x))ans+=c[x];
  return ans;
}
int seq[maxn];
bool cmp(const int &x,const int &y){
  return a[x]<a[y];
}
int main(){
   freopen("nt2011_queue.in","r",stdin);
   freopen("nt2011_queue.out","w",stdout);
  scanf("%d",&n);
  for(int i=1;i<=n;++i)scanf("%d",a+i);
  for(int i=1;i<=n;++i)seq[i]=i;
  sort(seq+1,seq+n+1,cmp);
  int tot=0,old=-1;
  for(int i=1;i<=n;++i){
    if(a[seq[i]]!=old){
      old=a[seq[i]];++tot;
    }
    a[seq[i]]=tot;
  }
  long long ans=0;
  for(int i=1;i<=n;++i){
    ans+=sum(a[i]+1);add(a[i]);
  }printf("%lld\n",ans);
  build();
  scanf("%d",&m);
  int x,y;
  for(int i=1;i<=m;++i){
    scanf("%d%d",&x,&y);
    if(x>y)swap(x,y);
    if(a[x]<a[y])ans++;
    else if(a[x]>a[y])ans--;
    Remove(x,a[x]);Remove(y,a[y]);
    if(x+1<y){
      ans-=Qsmall(x+1,y-1,a[x]);ans+=Qlarge(x+1,y-1,a[x]);
      ans-=Qlarge(x+1,y-1,a[y]);ans+=Qsmall(x+1,y-1,a[y]);
    }
    swap(a[x],a[y]);
    Insert(x,a[x]);Insert(y,a[y]);
    printf("%lld\n",ans);
  }
  fclose(stdin);fclose(stdout);
  return 0;
}