zoukankan      html  css  js  c++  java
  • 分块+莫队||BZOJ3339||BZOJ3585||Luogu4137||Rmq Problem / mex

    题面:P4137 Rmq Problem / mex

    题解:先莫队排序一波,然后对权值进行分块,找出第一个没有填满的块,直接for一遍找答案。

    除了bzoj3339以外,另外两道题Ai范围都是1e9。显然最劣情况下答案是N,所以大于N的Ai都直接无视就可以。

    由于求的是最小的自然数,自然数包括0,所以要额外处理一下含有0的块。我这里是直接把0拖出来放在第0块了。

    代码:

     1 #include<cstdio>
     2 #include<cstring>
     3 #include<iostream>
     4 #include<algorithm>
     5 #include<cmath>
     6 using namespace std;
     7 inline int rd(){
     8     int f=1,x=0;char c=getchar();
     9     while(c<'0'||c>'9'){if(c=='-')f=-1; c=getchar();}
    10     while(c>='0'&&c<='9'){x=x*10+c-'0'; c=getchar();}
    11     return f*x;
    12 }
    13 const int maxn=200005,maxm=200005,max_block=500;
    14 int N,M,A[maxn],l,r,block,Ans[maxm],vis[maxn],cnt[max_block],num,belong[maxn];
    15 struct Q{
    16     int id,l,r;
    17 }q[maxm];
    18 inline bool cmp(const Q&a,const Q&b){
    19     if(belong[a.l]==belong[b.l])return a.r<b.r;
    20     return a.l<b.l;
    21 }
    22 inline void Add(int x){
    23     if(x<=N){
    24         if(vis[x]==0)cnt[belong[x]]++;
    25         vis[x]++;
    26     }
    27     return;
    28 }
    29 inline void Del(int x){
    30     if(x<=N){
    31         vis[x]--;
    32         if(vis[x]==0)cnt[belong[x]]--;
    33     }
    34     return;
    35 }
    36 int main(){
    37     N=rd();M=rd();
    38     block=sqrt(N);
    39     num=N/block;
    40     if(N%block)num++;
    41     for(int i=1;i<=N;i++){
    42         A[i]=rd();
    43         belong[i]=(i-1)/block+1;
    44     }
    45     belong[0]=0;
    46     for(int i=1;i<=M;i++){
    47         q[i].id=i;
    48         q[i].l=rd();
    49         q[i].r=rd();
    50     }
    51     sort(q+1,q+M+1,cmp);
    52     l=1;r=0;
    53     for(int i=1;i<=M;i++){
    54         int ql=q[i].l,qr=q[i].r,id=q[i].id;
    55         while(l<ql)Del(A[l++]);
    56         while(l>ql)Add(A[--l]);
    57         while(r<qr)Add(A[++r]);
    58         while(r>qr)Del(A[r--]);
    59         if(cnt[0]==0){
    60             Ans[id]=0;
    61             continue;
    62         }
    63         int t=-1;
    64         for(int j=1;j<=num;j++){
    65             if(j!=num&&cnt[j]!=block){
    66                 t=j;
    67                 break;
    68             }
    69             else if(cnt[j]!=N-(num-1)*block) t=j;
    70         }
    71         if(t==-1){
    72             Ans[id]=N;
    73             continue;
    74         }
    75         int f=(t-1)*block+1,toj=t*block;
    76         for(int j=f;j<=toj;j++)
    77             if(vis[j]==0){
    78                 Ans[id]=j;
    79                 break;
    80             }    
    81     }
    82     for(int i=1;i<=M;i++)printf("%d
    ",Ans[i]);
    83     return 0;
    84 }

    By:AlenaNuna

  • 相关阅读:
    【转】php三种工具pecl pear composer的区别
    【转】Git使用详细教程
    【转】chrome Network 过滤和高级过滤
    Python3第三方组件最新版本追踪实现
    Python3版本号比较代码实现
    模糊测试工具设计思路浅谈
    Python3+WebSockets实现WebSocket通信
    Python3+PyCryptodome实现各种加密算法教程
    HTTP漫谈
    Python3+Robot Framework+RIDE安装使用教程
  • 原文地址:https://www.cnblogs.com/AlenaNuna/p/10163840.html
Copyright © 2011-2022 走看看