萌新刚学分块,1WA19RE
查看原帖
萌新刚学分块,1WA19RE
113926
typedef楼主2020/8/26 20:18

RT,样例是能过
希望大佬帮忙看下

/*
数组没开够,爆零两行泪
longlong开成int,爆零两行泪
多组忘清空,爆零两行泪
 dp 没初值,爆零两行泪
深搜没边界,爆零两行泪
广搜忘出队,爆零两行泪
输入没加 &,爆零两行泪
模数没看见,爆零两行泪
 -1 不输出,爆零两行泪
越界不特判,爆零两行泪
线段树开一倍,爆零两行泪
无向变有向,爆零两行泪
题意没审清,爆零两行泪
文件名起错,爆零两行泪
调试忘删除,爆零两行泪
没用freopen,爆零两行泪
*/
#include<bits/stdc++.h>
using namespace std;
const int N=40006,T=37;//4w的三次方根 ,N是蒲公英的种类标记 
int a[N],b[N],L[N],R[N],pos[N],c[T][T][N],f[T][T][2],now[2];
inline void work(int x,int y,int num){
	++c[x][y][num];//c[0][0][a[i]]记录不是整块的蒲公英数量 
	if(c[x][y][num]>now[0]||c[x][y][num]==now[0]&&num<now[1]){
		now[0]=c[x][y][num];//打擂台 找数量最大的蒲公英,若一样,找编号小的那个 
		now[1]=num;//种类 
	}
	return; 
}
int ask(int l,int r){
	int p=pos[l],q=pos[r];
	int x=0,y=0;
	if(p+1<=q-1){
		x=p+1;
		y=q-1;//定位到完整块 
	}
	memcpy(now,f[x][y],sizeof(now));//备份最多几个,以及是第几种 
	if(p==q){//同一区间 不完整 
		for(int i=l;i<=r;i++){
			work(x,y,a[i]);//单独统计a[i]出现的次数 
		}
		for(int i=l;i<=r;i++){
			--c[x][y][a[i]];//消除影响,便于下次统计 
		}
	}
	else{
		for(int i=l;i<=R[p];i++) work(x,y,a[i]);
		for(int i=L[q];i<=r;i++) work(x,y,a[i]);
		for(int i=l;i<=R[p];i++) --c[x][y][a[i]];
		for(int i=L[q];i<=r;i++) --c[x][y][a[i]]; 
	}
	return b[now[1]];//对应的原数 
}
int main(){
//	freopen("testin.txt","r",stdin);
//	freopen("testout.txt","w",stdout);
	int n,m;
	cin>>n>>m;
	for(int i=1;i<=n;i++) scanf("%d",&a[i]);
	memcpy(b,a,sizeof(b));
	sort(b+1,b+n+1);
	int tot=unique(b+1,b+n+1)-b-1;//一共多少种
	for(int i=1;i<=n;i++){
		a[i]=lower_bound(b+1,b+tot+1,a[i])-b;//从1开始 
	}
	int t=pow((double)n,(double)1/3);
	int len=t?n/t:n;//块数小于1,一块长度n;大于1,长度t 
	for(int i=1;i<=t;i++){
		L[i]=(i-1)*len+1;
		R[i]=i*len; 
	}
	if(R[t]<n){
		L[t+1]=R[t]+1;
		R[++t]=n;
	}
	for(int i=1;i<=t;i++){
		for(int j=L[i];j<=R[i];j++){
			pos[j]=i;
		}
	}
	memset(c,0,sizeof(c));
	memset(f,0,sizeof(f));
	for(int i=1;i<=t;i++){
		for(int j=i;j<=n;j++){
			for(int k=L[i];k<=R[i];k++)
				++c[i][j][a[k]];//从第i分块到第j个分块,每种蒲公英的数量
			for(int k=1;k<=tot;k++){
				if(c[i][j][k]>=f[i][j][0]){
					f[i][j][0]=c[i][j][k];//最多数量是多少 
					f[i][j][i]=k;//具体哪(k)种数量最多
				}
			} 
		}
	}
	int x=0;
	while(m--){
		int l,r;
		scanf("%d%d",&l,&r);
		l=(l+x-1)%n+1;
		r=(r+x-1)%n+1;
		if(l>r) swap(l,r);
		x=ask(l,r);
		printf("%d\n",x); 
	}
	//分块预处理,统计每个块上蒲公英种类的数量 
	return 0;
}

2020/8/26 20:18
加载中...