玄关求小样例研究
查看原帖
玄关求小样例研究
238254
wv290123楼主2024/12/27 21:29
#include<bits/stdc++.h>
typedef long long ll;
const int maxn=3e5+10;
using namespace std;
struct s{
	int mxn,minn;
	int pre;
}tre[maxn<<2];
struct node{
	int d;
}tre1[maxn<<2];
map<int ,set<int> > vis;//前驱
map<int ,set<int> > vis1;//后继
int pre1[maxn];
int n,m;
int a[maxn],b[maxn];
int gcd(int a,int b){
	if(b==0 ) return a;
	else return gcd(b,a%b);
}
void pushup(int t){
	tre[t].minn=min(tre[t<<1].minn,tre[t<<1|1].minn );
	tre[t].mxn =max(tre[t<<1].mxn,tre[t<<1|1].mxn );
	tre[t].pre =max(tre[t<<1].pre,tre[t<<1|1].pre );
}
void build(int t,int l,int r){
	tre[t].mxn=tre[t].minn=tre[t].pre=0;
	if(l==r){
		tre[t].mxn=a[l];
		tre[t].minn=a[l];
		set<int>::iterator it=vis[a[l]].lower_bound((l-1)*(-1));
		pre1[l]=min(*it,0);
		set<int>::iterator it1=vis1[a[l]].lower_bound(l+1);
		tre[t].pre=pre1[l];
		return ;
	}
	int mid=l+r>>1;
	build(t<<1,l,mid);
	build(t<<1|1,mid+1,r);
	pushup(t);
}
void add(int t,int pos,int l,int r){
	if(l==r){
		tre[t].mxn=a[l];
		tre[t].minn=a[l];
		tre[t].pre=pre1[l];
		return ;
	}
	int mid=l+r>>1;
	if(pos<=mid) add(t<<1,pos,l,mid);
	else add(t<<1|1,pos,mid+1,r);
	pushup(t);
}
s query(int t,int l1,int r1,int l,int r){
	if(l1<=l&&r<=r1){
		return tre[t];
	}
	s num;
	int mid=l+r>>1;
	if(l1<=mid) num=query(t<<1,l1,r1,l,mid);
	if(r1>mid){
		if(l1<=mid){
			s num2=query(t<<1|1,l1,r1,mid+1,r);
			num.minn =min(num.minn ,num2.minn );
			num.mxn =max(num.mxn ,num2.mxn );
			num.pre =max(num.pre,num2.pre );
		}
		else
			num=query(t<<1|1,l1,r1,mid+1,r) ;
	}
	return num;
}

void pushup1(int t){
	tre1[t].d=gcd(tre1[t<<1].d,tre1[t<<1|1].d );
}
void build1(int t,int l,int r){
	if(l==r){
		tre1[t].d=abs(a[l+1]-a[l]);
		return ;
	}
	int mid=l+r>>1;
	build1(t<<1,l,mid);
	build1(t<<1|1,mid+1,r);
	pushup1(t);
}
void add1(int t,int pos,int l,int r){
	if(l==r){
		tre1[t].d=abs(a[l+1]-a[l]);
		return ;
	}
	int mid=l+r>>1;
	if(pos<=mid) add(t<<1,pos,l,mid);
	else add(t<<1|1,pos,mid+1,r);
	pushup1(t);
}
int query1(int t,int l1,int r1,int l,int r){
	if(l1<=l&&r<=r1){
		return tre1[t].d ;
	}
	int mid=l+r>>1;
	int ans;
	if(l1<=mid) ans=query1(t<<1,l1,r1,l,mid);
	if(r1>mid){
		if(l1<=mid) ans=gcd(ans,query1(t<<1|1,l1,r1,mid+1,r));
		else ans=query1(t<<1|1,l1,r1,mid+1,r);
	}
	return ans;
}
int main(){
	scanf("%d %d",&n,&m);
	for(int i=1;i<=n;i++){
		scanf("%d",&a[i]);
		vis[a[i]].insert(i*(-1));
		vis1[a[i]].insert(i);
	}
	build(1,1,n);
	build1(1,1,n-1);
	int cnt=0;
	for(int i=1;i<=m;i++){
		int op,x,y;
		scanf("%d %d %d",&op,&x,&y);
		if(op==1&&x==6) 
			int ads=1;
		x=x^cnt;
		y=y^cnt;
		if(op==1){
			if(x>n) continue;
		//	cerr<<"innnn\n";
			auto it=vis[a[x]].lower_bound(x*(-1));
			if(it!=vis[a[x]].end())vis[a[x]].erase(it);	
			
			auto it1=vis1[a[x]].lower_bound(x+1);
			it=vis[a[x]].lower_bound((x-1)*(-1));
			if(it1!=vis1[a[x]].end()){	
				pre1[*it1]=min(*it,0)*(-1);
				add(1,*it1,1,n);
			}	
			
		///	cerr<<"outtt\n";
			it=vis1[a[x]].lower_bound(x);
			if(it!=vis1[a[x]].end())vis1[a[x]].erase(it);
			
			a[x]=y;
			vis[a[x]].insert(x*(-1));
			vis1[a[x]].insert( x);
			add(1,x,1,n);
			it1=vis1[a[x]].lower_bound(x+1);
			it=vis[a[x]].lower_bound((x-1)*(-1));
			pre1[x]=min(*it,0)*(-1);
			if(it1!=vis1[a[x]].end()){
				add(1,*it1,1,n);
			}	
			if(x!=1) add1(1,x-1,1,n);
			if(x!=n) add1(1,x,1,n);
		}
		else{
			int k;
			scanf("%d",&k);
		//	cout<<x<<" "<<y<<endl;
			if(x>y){
				cout<<"No"<<endl;
				continue;
			}
			if(x==y){
				printf("Yes\n");
				cnt++;
				continue;
			}
			k=k^cnt;
			s num1=query(1,x,y,1,n);
			int d=query1(1,x,y-1,1,n-1);
			if((ll)(num1.mxn -num1.minn)==(ll)(y-x)*k&&d==k&&num1.pre<x){
				printf("Yes\n");
				cnt++;
			}
			else
				printf("No\n");
		}
	}
	return 0;
}

码风比较丑陋,全wa,大佬求助%%%%

2024/12/27 21:29
加载中...