poj3294 Life Forms(后缀数组+二分答案)
来源:互联网 发布:linux 发送post请求 编辑:程序博客网 时间:2024/05/28 23:10
求在≥k个串中出现过的最长子串.还是先都连起来,用特殊字符隔开,然后二分答案,按h分组,在一组内统计出现过的子串,满足条件就更新,注意可能有多个子串满足条件,按照顺序存下来就好了。大坑点见注释。(有人就拿char过了,很神。)
#include <cstdio>#include <cstring>#define N 102000int s[N];bool blank=0,vis[110];int belong[N],n,k,ans[N];int count[N],rank[N<<1],rank1[N],sa[N],tmp[N],h[N];inline int max(int x,int y){return x>y?x:y;}inline bool jud(int x){memset(vis,0,sizeof(vis));int num=0,cnt=0;for(int i=1;i<=n+1;++i){if(h[i]>=x){if(!vis[belong[sa[i]]]) vis[belong[sa[i]]]=1,cnt++;if(!vis[belong[sa[i-1]]]) vis[belong[sa[i-1]]]=1,cnt++;}else{if(cnt>k/2) ans[++num]=sa[i-1];cnt=0;memset(vis,0,sizeof(vis));}}if(num){ans[0]=num;return 1;} else return 0;}int main(){//freopen("a.in","r",stdin);//freopen("a.out","w",stdout);while(1){n=0;int r=0;char str[1010]; scanf("%d",&k);if(!k) break;for(int i=1;i<=k;++i){//一定要转成int去做,char实在是伤不起啊。。//char 8字节,最高位符号位,所以当数值>127时就会变负的啊!//以后再也不要用char做了。。 scanf("%s",str+1);int len=strlen(str+1);r=max(r,len);for(int j=1;j<=len;++j) s[++n]=str[j]-'a'+1,belong[n]=i;s[++n]=100+i;belong[n]=i;}memset(count,0,sizeof(count));memset(rank,0,sizeof(rank));memset(h,0,sizeof(h));for(int i=1;i<=n;++i) count[s[i]]=1;for(int i=1;i<=200;++i) count[i]+=count[i-1];for(int i=n;i>=1;--i) rank[i]=count[s[i]];int kk=0;for(int p=1;kk!=n;p<<=1){memset(count,0,sizeof(count));for(int i=1;i<=n;++i) count[rank[i+p]]++;for(int i=1;i<=n;++i) count[i]+=count[i-1];for(int i=n;i>=1;--i) tmp[count[rank[i+p]]--]=i;memset(count,0,sizeof(count));for(int i=1;i<=n;++i) count[rank[tmp[i]]]++;for(int i=1;i<=n;++i) count[i]+=count[i-1];for(int i=n;i>=1;--i) sa[count[rank[tmp[i]]]--]=tmp[i];memcpy(rank1,rank,sizeof(rank1));rank[sa[1]]=kk=1;for(int i=2;i<=n;++i){if(rank1[sa[i]]!=rank1[sa[i-1]]||rank1[sa[i]+p]!=rank1[sa[i-1]+p]) ++kk;rank[sa[i]]=kk;}}kk=0;for(int i=1;i<=n;++i){if(rank[i]==1){h[1]=0;continue;}if(i==1||h[rank[i-1]]<=1) kk=0;if(kk) --kk;while(s[i+kk]==s[sa[rank[i]-1]+kk]) ++kk;h[rank[i]]=kk;}int l=1;while(l<=r){int mid=(l+r)>>1;if(jud(mid)) l=mid+1;else r=mid-1;}if(blank) puts("");else blank=1;if(l==1) puts("?");else for(int i=1;i<=ans[0];++i){for(int j=0;j<l-1;++j) putchar(s[ans[i]+j]+'a'-1);puts("");}}return 0;}
阅读全文
0 0
- poj3294 Life Forms(后缀数组+二分答案)
- 【POJ3294】Life Forms【后缀数组】【二分】
- [POJ3294]Life Forms(后缀数组+二分)
- POJ3294---Life Forms(后缀数组,二分+给后缀分组)
- POJ3294:Life Forms(后缀数组)
- 后缀数组 - poj3294 Life Forms
- poj3294 Life Forms - 后缀数组
- POJ3294 Life Forms 【后缀数组】
- poj3294 Life Forms(后缀数组)
- POJ3294-Life Forms(后缀数组)
- POJ3294——Life Forms 后缀数组
- Poj 3294 Life Forms(后缀数组+二分答案)
- poj3294 二分+后缀数组
- poj 3294 Life Forms(后缀数组+二分)
- UVA 11107(Life Forms-后缀数组+二分)
- [后缀数组+二分] poj 3294 Life Forms
- Uva 11107 Life Forms(后缀数组 + 二分)
- poj_3294 Life Forms(后缀数组+二分)
- Apache Solr基本配置
- 1101: [POI2007]Zap/2045: 双亲数/2301: [HAOI2011]Problem b
- BZOJ 3524 主席树(随机数水过) 解题报告
- [展览人周刊]华展云20170710期
- canvas元素的总结
- poj3294 Life Forms(后缀数组+二分答案)
- Oracle JDK7 and JRE7 认证过的系统配置
- JQuery选择器和jsp
- 树莓派3如何安装FreeBSD
- etcd+confd实现docker无状态部署
- 算法导论2.3-7
- 归并排序
- macOS Sierra开启HiDPI的方法
- 小程序setData