zoukankan      html  css  js  c++  java
  • 【题解】NOIO2020 冒泡排序(树状数组)

    【题解】NOIO2020 冒泡排序(树状数组)

    考虑在k次冒泡后的排列中的一个逆序对(i<j,a_i>a_j)

    因为这个(a_i)的存在,意味着(a_j)没有被往右边交换过(否则不会存在一个(a_i>a_j))。

    对于每个没有被交换到右边的数,他前面总共有(k)个比他大的数被交换走了。记(ans[i])表示原序列(i)位置和之前的数构成的逆序对个数,那么(k)次交换后,对答案的贡献是(ans[i]-k)

    那么答案就是

    [sum max(0, ext{ans}[i]-k) ]

    (ans[i])的值域开两个树状数组,每次取所有大于(k)的所有(ans)之和,再减去(ans[i]>k)的个数乘以(k)就是答案。两个操作都是取一段后缀,直接树状数组即可。

    至于交换操作,由于只影响了两个(ans),所以直接模拟一遍就行。

    复杂度(O(nlog n))。注意(k)要对(n-1)取min。

    //@winlere
    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    
    using namespace std;  typedef long long ll;  
    inline int qr(){
    	int ret=0,f=0,c=getchar();
    	while(!isdigit(c)) f|=c==45,c=getchar();
    	while( isdigit(c)) ret=ret*10+c-48,c=getchar();
    	return f?-ret:ret;
    }
    const int maxn=2e5+5;
    int data[maxn],n,m;
    ll seg1[maxn],seg2[maxn];
    void add(ll*seg,int pos,ll val){
    	++pos;
    	for(int t=pos;t<=n+1;t+=t&-t)
    		seg[t]+=val;
    }
    ll que(ll*seg,int pos){
    	++pos;
    	ll ret=0;
    	for(int t=pos;t>0;t-=t&-t)
    		ret+=seg[t];
    	return ret;
    }
    ll que(ll*seg,int l,int r){return que(seg,r)-que(seg,l-1);}
    int ans[maxn];
    void del(int pos){add(seg1,ans[pos],-ans[pos]); add(seg2,ans[pos],-1);}
    void add(int pos){add(seg1,ans[pos],ans[pos]); add(seg2,ans[pos],1);}
    
    int main(){
    	n=qr(); m=qr();
    	for(int t=1;t<=n;++t)
    		data[t]=qr(),ans[t]=t-1-que(seg1,data[t]),add(seg1,data[t],1);
    	memset(seg1,0,sizeof seg1);
    	for(int t=1;t<=n;++t) add(t);
    	for(int t=1;t<=m;++t){
    		int op=qr(),x=min(qr(),n);
    		if(op==1){
    			del(x),del(x+1);
    			ans[x+1]-=data[x]>data[x+1];
    			swap(data[x],data[x+1]); swap(ans[x],ans[x+1]);
    			ans[x+1]+=data[x]>data[x+1];
    			add(x),add(x+1);
    		}else{
    			ll ret=que(seg1,x,n)-que(seg2,x,n)*x;
    			printf("%lld
    ",ret);
    		}
    	}
    	return 0;
    }
    
    
  • 相关阅读:
    eslint 入门学习
    sqlite数据库 select 查询带换行符数据
    (ios)ARC常用设置,部分文件编译设置ARC
    (ios实战)ios调试总结(转载)
    IOS沙盒Files目录说明和常用操作
    (Ios 实战) 自定义UITableView
    iphone,pad等真机不被xcode识别,解决方法
    Xcode模拟器和真机生成的日志查看(转载)
    项目管理(转载)
    互联网教育,未来当有这10个特质(转载)
  • 原文地址:https://www.cnblogs.com/winlere/p/12434056.html
Copyright © 2011-2022 走看看