社区讨论

acwing246求助

灌水区参与者 2已保存回复 2

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
2 条
当前快照
1 份
快照标识符
@luv4p97w
此快照首次捕获于
2024/04/11 19:01
2 年前
此快照最后确认于
2024/04/11 20:56
2 年前
查看原帖
被卡常MEL了咋办
CPP
//gcd(a,b,c...x)=gcd(a,b-a,c-b...x-w)
#include<bits/stdc++.h>
using namespace std;
#define ls pos<<1
#define rs pos<<1|1
#define int long long
const int MAXN=5e5+5;
struct Segment_Tree
{
	int l,r;
	int gcd;
}tree[MAXN*4];
struct segment_tree
{
	int l,r;
	int add,sum;
}Tree[MAXN*4];
int N,M;
int a[MAXN];
int c[MAXN];
int gcd(int x,int y)
{
    if(x<0) x=-x;
    if(y<0) y=-y;
	if(x<y) swap(x,y);
	if(!y) return x;
	return gcd(y,x%y);
}
void update(int pos)
{
	Tree[pos].sum=Tree[ls].sum+Tree[rs].sum;
}
void build(int pos,int l,int r)
{
	Tree[pos].l=l;Tree[pos].r=r;
	if(l==r)
	{
		Tree[pos].sum=a[l];
		return;
	}
	int mid=(l+r)>>1;
	build(ls,l,mid);
	build(rs,mid+1,r);
	update(pos);
}
void push_down(int pos)
{
	Tree[ls].sum+=Tree[pos].add*(Tree[ls].r-Tree[ls].l+1);
	Tree[ls].add+=Tree[pos].add;
	Tree[rs].sum+=Tree[pos].add*(Tree[rs].r-Tree[rs].l+1);
	Tree[rs].add+=Tree[pos].add;
	Tree[pos].add=0;
}
void modify(int pos,int l,int r,int del)
{
	if(l<=Tree[pos].l&&Tree[pos].r<=r)
	{
		Tree[pos].sum+=del*(Tree[pos].r-Tree[pos].l+1);
		Tree[pos].add+=del;
		return; 
	}
	if(Tree[pos].add) push_down(pos);
	int mid=(Tree[pos].l+Tree[pos].r)>>1;
	if(l<=mid) modify(ls,l,r,del);
	if(mid+1<=r) modify(rs,l,r,del);
	update(pos);
}
int ask(int pos,int x)
{
	if(Tree[pos].l==Tree[pos].r)
	{
		return Tree[pos].sum;
	}
	if(Tree[pos].add) push_down(pos);
	int mid=(Tree[pos].l+Tree[pos].r)>>1;
	int cal=0;
	if(x<=mid) cal=ask(ls,x);
	else cal=ask(rs,x);
	return cal;
}
void Update(int pos)
{
	tree[pos].gcd=gcd(tree[ls].gcd,tree[rs].gcd);
}
void Build(int pos,int l,int r)
{
	tree[pos].l=l;tree[pos].r=r;
	if(l==r)
	{
		tree[pos].gcd=c[l];
		return ;
	}
	int mid=(l+r)>>1;
	Build(ls,l,mid);
	Build(rs,mid+1,r);
	Update(pos);
}
void Modify(int pos,int x,int del)
{
	if(tree[pos].l==tree[pos].r)
	{
		tree[pos].gcd+=del;
		return ;
	}
	int mid=(tree[pos].l+tree[pos].r)>>1;
	if(x<=mid) Modify(ls,x,del);
	else Modify(rs,x,del);
	Update(pos);
}
int Ask(int pos,int l,int r)
{
	if(l<=tree[pos].l&&tree[pos].r<=r)
	{
		return tree[pos].gcd;
	}
	int mid=(tree[pos].l+tree[pos].r)>>1;
	int cal=0;
	if(l<=mid) cal=gcd(cal,Ask(ls,l,r));
	if(mid+1<=r)  cal=gcd(cal,Ask(rs,l,r));
	return cal; 
}
signed main()
{
    ios::sync_with_stdio(0);
    cin.tie(0);
	cin>>N>>M;
	for(int i=1;i<=N;i++) cin>>a[i];
	for(int i=1;i<=N;i++) c[i]=a[i]-a[i-1];
	build(1,1,N);
	Build(1,1,N);
	for(int i=1;i<=M;i++)
	{
		char opt;
		int l,r,del;
		cin>>opt;
		if(opt=='Q')
		{
			
			cin>>l>>r;
			printf("%lld\n",gcd(ask(1,l),Ask(1,l+1,r)));
		}
		else
		{
			cin>>l>>r>>del;//al,al+1...ar + del <=> c[l]+del,c[r+1]-del
			modify(1,l,r,del);
			Modify(1,l,del);
			if(r+1<=N) Modify(1,r+1,-del); 
		}
	}
}

回复

2 条回复,欢迎继续交流。

正在加载回复...