zoukankan      html  css  js  c++  java
  • BZOJ 3207 花神的嘲讽计划Ⅰ

     题意:给定一个序列,每次询问区间 [l,r] 内是否存在一个长度为K的子串.

     由于K是固定的,字符串hash再离散,然后问题转化成了询问区间[l,r]内是否存在一个要求的数.

     可持久化线段树可切,离线乱搞同样支持,可以试下可持久化01Trie.

     

     1 #include<algorithm>
     2 #include<cstdio>
     3 using namespace std;
     4 #define ll long long
     5 #define FILE "dealing"
     6 #define up(i,j,n) for(int i=j;i<=n;i++)
     7 #define db long double 
     8 #define pii pair<int,int>
     9 #define pb push_back
    10 #define mem(a,L) memset(a,0,sizeof(int)*(L+1))
    11 template<class T> inline bool cmin(T& a,T b){return a>b?a=b,true:false;}
    12 template<class T> inline bool cmax(T& a,T b){return a<b?a=b,true:false;}
    13 template<class T> inline T squ(T a){return a*a;}
    14 const ll maxn=2000100+10,MAXN=200200,inf=1e9+10,limit=1e7,base=23;
    15 int read(){
    16     int x=0,f=1,ch=getchar();
    17     while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
    18     while(ch>='0'&&ch<='9')x=(x<<1)+(x<<3)+ch-'0',ch=getchar();
    19     return x*f;
    20 }
    21 
    22 unsigned long long hash[MAXN],k[MAXN];
    23 
    24 int n,M,K;
    25 int a[MAXN],w[MAXN],root[MAXN];
    26 struct query{
    27     int l,r;
    28     unsigned long long v;
    29 }q[MAXN];
    30 unsigned long long get(int l,int r){
    31     return hash[l]-hash[r+1]*k[r-l+1];
    32 }
    33 pair<unsigned long long,pii > t[MAXN];
    34 int val[MAXN],m;
    35 int cnt=0;
    36 int c[maxn][2],sum[maxn],Cnt=0;
    37 void updata(int o){
    38     sum[o]=sum[c[o][0]]+sum[c[o][1]];
    39 }
    40 void insert(int pre,int& o,int l,int r,int key){
    41     o=++Cnt;
    42     if(l==r){
    43         sum[o]=sum[pre]+1;
    44         return;
    45     }
    46     int mid=(l+r)>>1;
    47     if(key>mid)c[o][0]=c[pre][0],insert(c[pre][1],c[o][1],mid+1,r,key);
    48     else c[o][1]=c[pre][1],insert(c[pre][0],c[o][0],l,mid,key);
    49     updata(o);
    50 }
    51 bool query(int pre,int o,int l,int r,int key){
    52     int mid=(l+r)>>1;
    53     if(l==r||!(sum[o]-sum[pre]))return sum[o]-sum[pre];
    54     if(key>mid)return query(c[pre][1],c[o][1],mid+1,r,key);
    55     else return query(c[pre][0],c[o][0],l,mid,key);
    56 }
    57 int main(){
    58     freopen(FILE".in","r",stdin);
    59     freopen(FILE".out","w",stdout);
    60     n=read(),M=read(),K=read();
    61     up(i,1,n)a[i]=read();
    62     k[0]=1;up(i,1,n)k[i]=k[i-1]*base;
    63     for(int i=n;i>=1;i--)
    64         hash[i]=hash[i+1]*base+a[i];
    65     for(int i=1;i<=M;i++){
    66         q[i].l=read(),q[i].r=read();
    67         unsigned long long u=0;
    68         for(int j=1;j<=K;j++)w[j]=read();
    69         for(int j=K;j>=1;j--)u=u*base+w[j];
    70         q[i].v=u;
    71     }
    72     for(int i=1;i<=n-K+1;i++)
    73         t[++cnt]=make_pair(get(i,i+K-1),make_pair(i,1));
    74     for(int i=1;i<=M;i++)
    75         t[++cnt]=make_pair(q[i].v,make_pair(i,2));
    76     sort(t+1,t+cnt+1);
    77     for(int i=1;i<=cnt;i++){
    78         if(i==1||t[i].first!=t[i-1].first)m++;
    79         if(t[i].second.second==1)val[t[i].second.first]=m;
    80         else q[t[i].second.first].v=m;
    81     }
    82     for(int i=1;i<=n-K+1;i++)
    83         insert(root[i-1],root[i],1,m,val[i]);
    84     for(int i=1;i<=M;i++){
    85         if(query(root[q[i].l-1],root[q[i].r-K+1],1,m,q[i].v))printf("No
    ");
    86         else printf("Yes
    ");
    87     }
    88     return 0;
    89 }
    View Code

     

  • 相关阅读:
    【转】 java中Class对象详解和类名.class, class.forName(), getClass()区别
    106. Construct Binary Tree from Inorder and Postorder Traversal
    105. Construct Binary Tree from Preorder and Inorder Traversal
    107. Binary Tree Level Order Traversal II
    109. Convert Sorted List to Binary Search Tree
    108. Convert Sorted Array to Binary Search Tree
    110. Balanced Binary Tree
    STL容器迭代器失效问题讨论
    113. Path Sum II
    112. Path Sum
  • 原文地址:https://www.cnblogs.com/chadinblog/p/6809424.html
Copyright © 2011-2022 走看看