题解 SP18185 GIVEAWAY - Give Away

发布时间:2022-07-03 发布网站:脚本宝典
脚本宝典收集整理的这篇文章主要介绍了题解 SP18185 GIVEAWAY - Give Away脚本宝典觉得挺不错的,现在分享给大家,也给大家做个参考。

写一篇不用 vector 的分块题解

我们可以用一个b数组来代替a数组,然后使用分块的思想达到局部有序

如果是修改操作,单点修改后对一整个块进行重构

如果是查询,则整块使用lower_bound,散块暴力统计

复杂度是(O(msqrt{n}LOG sqrt{n}))

代码

#include <bITs/stdc++.h>
#define int long long
using namespace std;
const int N=5e5+10;
int a[N],b[N],pos[N],pl[N],PR[N],n,m,t,q;
inline int read(){
    int x=0,f=1;char ch=getchar();
    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 x*f;
}
void upd(int p,int val){
    a[p]=val;
    int P=pos[p];
    for(int i=pl[P];i<=pr[P];i++)
	b[i]=a[i];
    sort(b+pl[P],b+1+pr[P]);
}
int query(int l,int r,int c){
    int L=pos[l],R=pos[r],res=0;
    if(L==R){
	for(int i=l;i<=r;i++)
	    if(a[i]>=c) res++;
	return res;
    }
    for(int i=l;i<=pr[L];i++)
	if(a[i]>=c) res++;
    for(int i=pl[R];i<=r;i++)
	if(a[i]>=c) res++;
    for(int i=L+1;i<R;i++){
	int tot=lower_bound(b+pl[i],b+1+pr[i],c)-b-pl[i];
	res+=pr[i]-pl[i]-tot+1;
    }
    return res;
}
signed main(){
    n=read();
    t=sqrt(n);
    for(int i=1;i<=n;i++){
	b[i]=a[i]=read();
	pos[i]=(i-1)/t+1;
    }
    for(int i=1;i<=pos[n];i++){
	pl[i]=pr[i-1]+1,pr[i]=min(n,pl[i]+t-1);
	sort(b+pl[i],b+1+pr[i]);
    }
    q=read();
    for(int i=1;i<=q;i++){
	int c;
	cin>>c;
	if(c==0){
	    int x=read(),y=read(),z=read();
	    cout<<query(x,y,z)<<endl;
	}
	else{
	    int a=read(),b=read();
	    upd(a,b);
	}
    }
    return 0;
}

脚本宝典总结

以上是脚本宝典为你收集整理的题解 SP18185 GIVEAWAY - Give Away全部内容,希望文章能够帮你解决题解 SP18185 GIVEAWAY - Give Away所遇到的问题。

如果觉得脚本宝典网站内容还不错,欢迎将脚本宝典推荐好友。

本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
如您有任何意见或建议可联系处理。小编QQ:384754419,请注明来意。