放过平方和也就算了
查看原帖
放过平方和也就算了
179182
CCCCOrz楼主2021/1/13 20:27

我维护最大最小和一次和竟然也过了??? 记录

#include <cstdio>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
inline int mmin(const int &x,const int &y){return x<y?x:y;}
inline int mmax(const int &x,const int &y){return x>y?x:y;}
inline int rd(){
	register int x=0;
	register char c=getchar();
	while(c<'0'||c>'9')c=getchar();
	while(c>='0'&&c<='9')x=(x<<1)+(x<<3)+(c^48),c=getchar();
	return x;
}
int n,m,lans;
struct node{
	int mn,mx;
	ll sum;
	ull s2;
	inline node operator +(const node &x)const{
		return (node){mmin(mn,x.mn),mmax(mx,x.mx),sum+x.sum,s2+x.s2};
	}
}t[1200000];
inline ull id2(const int &x){
	switch(x%3){
		case 0:return (1ull*x*(x+1)/6)*(x<<1|1);
		case 1:return (x<<1|1)/3*(1ull*(x+1)*x/2);
		case 2:return 1ull*x*(x+1)/6*(x<<1|1);
	}
}
inline ll id(const int &x){return 1ll*x*(x+1)>>1;}
inline void refresh(const int &p){t[p]=t[p<<1]+t[p<<1|1];}
inline void chg(int l,int r,int p,const int &w,const int &v){
	if(l==r)return (void)(t[p]=(node){v,v,v,1ull*v*v});
	int mid=l+r>>1;
	if(w<=mid)chg(l,mid,p<<1,w,v);
	else chg(mid+1,r,p<<1|1,w,v);
	refresh(p);
}
inline node ginf(int l,int r,int p,const int &b,const int &e){
	if(b<=l&&e>=r)return t[p];
	int mid=l+r>>1;
	node ans;
	if(b<=mid){
		ans=ginf(l,mid,p<<1,b,e);
		if(e>mid)ans=ans+ginf(mid+1,r,p<<1|1,b,e);
	}
	else if(e>mid)ans=ginf(mid+1,r,p<<1|1,b,e);
	return ans;
}
inline void chk(const int &b,const int &e,const int &k){
	if(b==e)return (void)puts((++lans,"Yes"));
	const node frm=ginf(1,n,1,b,e);
	const int &a1=frm.mn,&as=frm.mx,ss=e-b+1;
	const ll &sum=frm.sum;
	const ull &sqm=frm.s2;
	puts((as-a1==k*(ss-1)&&sum==1ll*(a1+as)*ss/2/*&&sqm==k*(1ull*k*id2(ss-1)+1ull*a1*ss*(ss-1))+1ull*ss*a1*a1*/)?(++lans,"Yes"):"No");
}
int main(){
	n=rd(),m=rd();
	for(int i=1;i<=n;++i)chg(1,n,1,i,rd());
	for(int i=1,t,x,y;i<=m;++i){
		t=rd();
		if(t==1)x=rd()^lans,chg(1,n,1,x,rd()^lans);
		else x=rd()^lans,y=rd()^lans,chk(x,y,rd()^lans);
	}
	return 0;
}
2021/1/13 20:27
加载中...