萌新刚学第二分块 7.50s,求助哪里有问题/卡常
查看原帖
萌新刚学第二分块 7.50s,求助哪里有问题/卡常
508032
int08楼主2024/3/31 15:48

7 pts

#include<bits/stdc++.h>
#define N 100005
using namespace std;
bool mbegin;
int lb=1400;
inline int read(){
	register int x=0;
	register bool f=0;
	register char c=getchar();
	while(c<'0'||c>'9'){
		if(c=='-') f=1;
		c=getchar();
	}
	while(c>='0'&&c<='9'){
		x=(x<<3)+(x<<1)+c-48;
		c=getchar();
	}
	return f?-x:x;
}
char cr[200];int tt;
inline void write(register int x,register char k='\n') {
    if(!x) putchar('0');
    if(x < 0) putchar('-'),x=-x;
    while(x) cr[++tt]=x%10+'0',x/=10;
    while(tt) putchar(cr[tt--]);
    putchar(k);
}
struct bl{
	int mx,fa[5*N],mns,sz[5*N];
	void init()
	{
		for(register int i=1;i<=mx;i++) fa[i]=i;
	}
	int find(int x)
	{
		if(fa[x]==x) return x;
		else return fa[x]=find(fa[x]);
	}
}b;
int a[10*N],i,j,n,m,q,op[5*N],l[5*N],r[5*N],x[5*N];
#define bo(x) (((x)-1)/lb+1)
inline void single_change(int pos,int v)
{
	int act=b.find(a[pos]);
	if(act<=v+b.mns)
		return;
	a[pos]=act-v;
	b.sz[act]--;
	b.sz[act-v]++;
}
inline void block_change(int pos,int v)
{
	if(b.mx<=v+b.mns)
		return;
	int q=b.mx-b.mns;
	if(2*v>q)
	{
		for(register int i=v+b.mns;i<=b.mx;i++)
		{
			int ii=b.fa[i],iv=b.fa[i-v];
			b.sz[iv]+=b.sz[ii],b.sz[ii]=0;
			b.fa[ii]=b.fa[iv];
		}
		while(!b.sz[b.mx]) b.mx--;
	}
	else
	{
		for(register int i=1+b.mns;i<=v+b.mns;i++)
		{
			int ii=b.fa[i],iv=b.fa[i+v];
			b.sz[iv]+=b.sz[ii],b.sz[ii]=0;
			b.fa[ii]=b.fa[iv];
		}
		b.mns+=v;
	}
}
inline int single_ask(int pos,int v)
{
	int act=b.find(a[pos]);
	return (act==v+b.mns)?1:0;
}
inline int block_ask(int pos,int v)
{
	if(v+b.mns>v+b.mx) return 0;
	return b.sz[v+b.mns];
}
int ans[5*N];
bool mend;
int main()
{
	n=read();
	m=read();
	for(i=1;i<=n;i++) a[i]=read();
	for(j=1;j<=m;j++)
	{
		op[j]=read();l[j]=read();r[j]=read();x[j]=read();
	}
	int bln=bo(n);
	for(register int bli=1;bli<=bln;bli++)
	{
		memset(b.sz,0,sizeof(b.sz));
		b.mns=b.mx=0;
		for(i=lb*bli-lb+1;i<=min(lb*bli,n);i++)
		{
			b.sz[a[i]]++;
			b.mx=max(b.mx,a[i]);
		}
		b.init();
		for(j=1;j<=m;j++)
		{
#define l l[j]
#define r r[j]
#define op op[j]
#define x x[j]
			int lo=bo(l),ro=bo(r);
			if(op==1)
			{
				if(lo==bli)
					for(i=l;i<=min(r,lo*lb);i++)
						single_change(i,x);
				b.mx=0;
				for(i=(lo-1)*lb+1;i<=lo*lb;i++)
					b.mx=max(b.mx,b.find(a[i]));
				if(lo!=ro&&ro==bli)
				{
					for(i=(ro-1)*lb+1;i<=r;i++) single_change(i,x);
					b.mx=0;
					for(i=(ro-1)*lb+1;i<=min(r,lo*lb);i++)
						b.mx=max(b.mx,b.find(a[i]));
				}
				if(bli>lo&&bli<ro) block_change(bli,x);
			}
			if(op==2)
			{
				int an=0;
				if(lo==bli)
					for(i=l;i<=min(r,lo*lb);i++) an+=single_ask(i,x);
				if(lo!=ro&&ro==bli) for(i=(ro-1)*lb+1;i<=r;i++) an+=single_ask(i,x);
				if(bli>lo&&bli<ro) an+=block_ask(bli,x);
				ans[j]+=an;
			}
		}
	}
	for(j=1;j<=m;j++)
		if(op==2) write(ans[j]);
	return 0;
}
2024/3/31 15:48
加载中...