• CF1446D. Frequency Problem


    题目大意

    长为n的序列,求最长众数非唯一子串长度

    n<=2e5,ai<=n

    D1:ai<=min(100,n)

    题解

    D1:

    枚举右端点,显然随着左端点不断右移,一定有某个时刻众数非唯一,因此求出当前众数与其他的相等的最小l之后对长度取max

    每次+1-1只会改变1所以用桶维护,因为不好直接存所以写了链表

    实际上只需要考虑[1,n]的众数即可,比赛时并没有注意到虽然也能过

    D2:

    首先写一个空间线性的D1,然后平衡规划,这样是O(n√n)

    然后又被ll爆标了

    D1的瓶颈在于每次要把所有的值找一遍,现在按非众数来分段,那么总数就是O(n)的

    设众数为+1,非众数为-1

    之后+1变成段,-1变成点,对每种值维护这个东西,跳就暴力跳,因为跳-1的次数为O(n),跳+1直到跳到当前max的次数和-1相当(把-1看作势能),也是O(n)

    如果当前是-1就记下位置,否则位置一定是某个众数的位置,把众数提出来后记是第几个即可

    先给每种权值分配好空间,之后就可以时空O(n)解决

    code

    #include <bits/stdc++.h>
    #define fo(a,b,c) for (a=b; a<=c; a++)
    #define fd(a,b,c) for (a=b; a>=c; a--)
    #define max(a,b) (a>b?a:b)
    #define min(a,b) (a<b?a:b)
    #define ll long long
    //#define file
    using namespace std;
    
    int Sum[200002],sum[200002],a[200002],L[200002],R[200002],n,i,j,k,l,mx,mx2,ans;
    int ls[200002],d[800001][2],b[200002],c[200002],f[800001],I[200002],id[200002];
    
    int get(int t,int x)
    {
    	if (f[t]<=0) return -f[t];
    	return I[f[t]+(x-d[t][0])];
    }
    
    void work(int i,int s)
    {
    	int j,k,l;
    	l=sum[i]-sum[ls[s]];
    	while (l && b[s]<=R[s])
    	{
    		k=get(b[s],c[s]),ans=max(ans,(I[id[s]+1]-1)-k);
    		if (c[s]==d[b[s]][1]) ++b[s];
    		--l,++c[s],++id[s];
    	}
    	if (b[s]>R[s]) ++R[s],d[R[s]][0]=d[R[s]-1][1]+1,d[R[s]][1]=c[s]+l,f[R[s]]=id[s],id[s]+=l,c[s]+=l;
    	
    	k=get(b[s],c[s]),ans=max(ans,(i-1)-k);
    	if (i<=n)
    	{
    		if (c[s]==d[b[s]][0])
    		{
    			if (b[s]==L[s])
    			{
    				--L[s];
    				d[L[s]][0]=d[L[s]][1]=d[L[s]+1][0]-1;
    				f[L[s]]=-i;
    			}
    			--b[s];
    		}
    		--c[s];
    	}
    	ls[s]=i;
    }
    
    int main()
    {
    	#ifdef file
    	freopen("CF1446D.in","r",stdin);
    //	freopen("b.out","w",stdout);
    	#endif
    	
    	scanf("%d",&n);
    	fo(i,1,n)
    	{
    		scanf("%d",&a[i]),++Sum[a[i]];
    		if (Sum[a[i]]>mx) mx=Sum[a[i]],mx2=a[i];
    	}
    	fo(i,1,n+1) sum[i]=sum[i-1]+(a[i]==mx2);
    	
    	k=l=0;
    	fo(i,1,n)
    	if (i!=mx2)
    	b[i]=l+(Sum[i]+1),L[i]=R[i]=b[i],c[i]=0,d[b[i]][0]=d[b[i]][1]=0,l+=Sum[i]*2+2;
    	fo(i,1,n) if (a[i]==mx2) I[++k]=i;
    	
    	fo(i,1,n) if (a[i]!=mx2) work(i,a[i]);
    	fo(i,1,n) if (i!=mx2) work(n+1,i);
    	printf("%d
    ",ans);
    	
    	fclose(stdin);
    	fclose(stdout);
    	return 0;
    }
    
  • 相关阅读:
    腾讯Techo开发者大会PPT分享
    构建三维一体立体化监控,看这一篇就够了!
    ACOUG 联合创始人盖国强:万象更新,数据库技术和生态的发展演进
    全局配置项set_global_options 支持的opts
    InitOpts:初始化配置项:
    数据结构第四章树和森林,期末不挂科指南,第7篇
    Netflix:当你按下“播放”的时候发生了什么?
    Netflix:当你按下“播放”的时候发生了什么?
    搭建vsftpd文件服务器并创建虚拟用户
    搭建vsftpd文件服务器并创建虚拟用户
  • 原文地址:https://www.cnblogs.com/gmh77/p/14006390.html
Copyright © 2020-2023  润新知