• [Poj3261] [Bzoj1717] [后缀数组论文例题,USACO 2006 December Gold] Milk Patterns [后缀数组可重叠的k次最长重复子串]


    和上一题(POJ1743,上一篇博客)相似,只是二分的判断条件是:是否存在一段后缀的个数不小于k

     1 #include <iostream>
     2 #include <algorithm>
     3 #include <cstdio>
     4 #include <cstdlib>
     5 #include <cstring>
     6 #include <cmath>
     7 #include <ctime>
     8 #include <map>
     9 
    10 using namespace std;
    11 
    12 int    t;
    13 int    str[21000],A[21000],B[21000],U[21000],Tmp[21000],SA[21000],H[21000];
    14 map <int,int>    Map;
    15 
    16 void    Calc_H(const int n,const int * Rank)
    17 {
    18     int    i,j,k=0;
    19     for(i=0;i<n;H[Rank[i++]]=k)
    20         for(k?k--:0,j=SA[Rank[i]-1];str[i+k]==str[j+k];++k);
    21     return ;
    22 }
    23 
    24 bool    cmp(const int * s,const int a,const int b,const int l)
    25 {
    26     return s[a]==s[b] && s[a+l]==s[b+l];
    27 }
    28 
    29 int*    Get_SA(const int n,int    m)
    30 {
    31     int    i,j,p,*x=A,*y=B;
    32 
    33     for(i=0;i<n;++i)U[i]=0;
    34     for(i=0;i<n;++i)U[x[i]=str[i]]++;
    35     for(i=1;i<m;++i)U[i]+=U[i-1];
    36     for(i=n-1;i>=0;--i)SA[--U[x[i]]]=i;
    37 
    38     for(j=1,p=1;p<n;j<<=1,m=p)
    39     {
    40         for(p=0,i=n-j;i<n;++i)y[p++]=i;
    41         for(i=0;i<n;++i)if(SA[i]>=j)y[p++]=SA[i]-j;
    42         for(i=0;i<n;++i)Tmp[i]=x[y[i]];
    43         for(i=0;i<m;++i)U[i]=0;
    44         for(i=0;i<n;++i)U[Tmp[i]]++;
    45         for(i=1;i<m;++i)U[i]+=U[i-1];
    46         for(i=n-1;i>=0;--i)SA[--U[Tmp[i]]]=y[i];
    47         for(swap(x,y),p=1,x[SA[0]]=0,i=1;i<n;++i)
    48         x[SA[i]]=cmp(y,SA[i-1],SA[i],j)?p-1:p++;
    49     }
    50 
    51     Calc_H(n,x);
    52     return x;
    53 }
    54 
    55 bool    Check(const int lim,const int n)
    56 {
    57     int    cnt=0;
    58     for(int i=1;i<=n;++i)
    59     {
    60         if(i>1 && H[i]<lim)
    61         {
    62             if(cnt>=t)return true;
    63             cnt=1;
    64         }
    65         if(H[i]>=lim)cnt++;
    66     }
    67     if(cnt>=t)return true;
    68     return false;
    69 }
    70 
    71 int main()
    72 {
    73     int    i,l,r,n,cnt=0;
    74 
    75     scanf("%d%d",&n,&t);
    76     for(i=0;i<n;++i)
    77     {
    78         scanf("%d",&str[i]);
    79         if(!Map[str[i]])Map[str[i]]=++cnt;
    80         str[i]=Map[str[i]];
    81     }
    82 
    83     Get_SA(n+1,21000);
    84 
    85     l=0;r=n;
    86     while(l<r-1)
    87     {
    88         int    mid=l+((r-l)>>1);
    89         if(Check(mid,n))l=mid;
    90         else    r=mid;
    91     }
    92 
    93     printf("%d
    ",l);
    94 
    95     return 0;
    96 }
    View Code
  • 相关阅读:
    gazebo自建小车备忘
    关于hokuyo的一些参数的备忘
    xenserver加入池报错The servers in this pool are not homogeneous
    exchange管理控制台初始化失败--Kerberos连接失败
    修复windows系统更新失败
    powershell同步时间
    powershell创建密文密码文件
    powershell常用命令
    Graylog客户端及服务端
    powershell,cmd,shell查看帮助
  • 原文地址:https://www.cnblogs.com/Gster/p/4977968.html
Copyright © 2020-2023  润新知