蒲公英

Posted 2462478392lee

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了蒲公英相关的知识,希望对你有一定的参考价值。

题意:给N个数,求一个区间内的众数。

思路:分块,分成sqrt(t*log2(n)))块,先预处理出每一个块到每个块中的众数,离散化,然后把询问区间分三段,第一段为l到l所在块的终止,第二段为每一段块,第三段为r块的开始到r,然后第二段用预处理的数组就能得出,第一三段,二分vector记录的下标求众数。

 

#include<cstring>
#include<algorithm>
#include<vector>
#include<map>
#include<queue>
#include<cstdio>
#include<cmath>
#define ll long long
#define lowbit(x) x&(-x)
using namespace std;
const int N=1e6+10;
int n,t,block;
int a[N],f[N],b[N];
vector<int> g[N];
int c[N],d[1000][1000];
void build()

    block=max(1,(int)(n/sqrt(t*log2(n))));
    for(int i=1;i<=n;i++)
    b[i]=(i-1)/block+1;

int Count(int l,int r,int val)

    int t=upper_bound(g[val].begin(),g[val].end(),r)-lower_bound(g[val].begin(),g[val].end(),l);
    return t;
  
void pre(int x)

    memset(c,0,sizeof(c));
    int mx=-1,ans=0;
    for(int i=(x-1)*block+1;i<=n;i++)
    
        c[a[i]]++;
        if(c[a[i]]>mx||(c[a[i]]==mx&&a[i]<ans))
        
            ans=a[i];
            mx=c[a[i]];
        
        d[x][b[i]]=ans;//代表x到b[i]块的众数。 
    

int query(int l,int r)

    int ans=d[b[l]+1][b[r]-1];
    int mx=Count(l,r,ans);
    int cnt=0;
    int up=min(r,b[l]*block);
    for(int i=l;i<=up;i++)
    
        cnt=Count(l,r,a[i]);
        if(cnt>mx||(cnt==mx&&f[ans]>f[a[i]]))
        
            mx=cnt;
            ans=a[i];
        
    
    if(b[l]!=b[r])
    
        for (int i=(b[r]-1)*block+1;i<=r;i++)
        
            cnt=Count(l,r,a[i]);
            if(cnt>mx||(cnt==mx&&ans>a[i]))
            
                mx=cnt;
                ans=a[i];
            
        
    
    return ans;

signed main()

    scanf("%d%d",&n,&t);
    for(int i=1;i<=n;i++)
    
        scanf("%d",&a[i]);
        f[i]=a[i];
    
    build();
    sort(f+1,f+n+1);
    int m=unique(f+1,f+n+1)-f-1;
    for(int i=1;i<=n;i++)
    
        a[i]=lower_bound(f+1,f+m+1,a[i])-f;
        g[a[i]].push_back(i);
    
    for(int i=1;i<=b[n];i++)
    
        pre(i);
    
    int ans=0;
    while(t--)
    
        int l,r;
        scanf("%d%d",&l,&r);
        l=(l+ans-1)%n+1;
        r=(r+ans-1)%n+1;
        if(l>r)
        swap(l,r);
        ans=f[query(l,r)];
        printf("%d\n",ans);
    

 

以上是关于蒲公英的主要内容,如果未能解决你的问题,请参考以下文章

蒲公英 解题报告

蒲公英

Luogu P4168 [Violet]蒲公英

「Violet」蒲公英

Jenkins + 蒲公英 自动发布两个小技巧

蒲公英的约定