hdu_3518_Boring counting(后缀数组)
题意:
给你一个字符串,让你找不重叠且出现大于1次以上的字串个数
题解:
后缀数组height数组的应用,我们枚举字串的长度,然后将height数组分段,符合条件就ans++
为什么要这样做,因为height数组存的是相邻排名后缀的最大前缀数,如果height的值大于等于我们枚举的长度len,
那么有可能这一段存在有两个以上的该长度的字串,然后我们统计这个段的开头长度l和结束长度r,如果r-l>=len,说明这段必有
大于一个以上的该长度的相同子串,因为我们每次都是枚举len,按len分的段,所以不会重复。
#include<bits/stdc++.h>
#define F(i,a,b) for(int i=a;i<=b;++i)
using namespace std; namespace suffixarray{
#define FN(n) for(int i=0;i<n;i++)
const int N =1E3+;
int rnk[N],sa[N],height[N],c[N];char s[N];
void getsa(int n,int m,int *x=rnk,int *y=height){
FN(m)c[i]=;FN(n)c[x[i]=s[i]]++;FN(m)c[i+]+=c[i];
for(int i=n-;i>=;i--)sa[--c[x[i]]]=i;
for(int k=,p;p=,k<=n;k=p>=n?N:k<<,m=p){
for(int i=n-k;i<n;i++)y[p++]=i;
FN(n)if(sa[i]>=k)y[p++]=sa[i]-k;
FN(m)c[i]=;FN(n)c[x[y[i]]]++;FN(m)c[i+]+=c[i];
for(int i=n-;i>=;i--)sa[--c[x[y[i]]]]=y[i];
swap(x,y),p=,x[sa[]]=;
for(int i=;i<n;i++)
x[sa[i]]=y[sa[i-]]==y[sa[i]]&&y[sa[i-]+k]==y[sa[i]+k]?p-:p++;
}
FN(n)rnk[sa[i]]=i;
for(int i=,j,k=;i<n-;height[rnk[i++]]=k)
for(k=k?k-:k,j=sa[rnk[i]-];s[i+k]==s[j+k];k++);
}
} inline void upd(int &a,int b){if(a>b)a=b;}
inline void upu(int &a,int b){if(a<b)a=b;} using namespace suffixarray;
int main(){
while(~scanf("%s",s))
{
if(s[]=='#')break;
int len=strlen(s),ans=;
getsa(len+,);
F(i,,len)
{
int l=len+,r=;
F(j,,len)
{
if(height[j]>=i)upd(l,sa[j]),upu(r,sa[j]);
else
{
if(r-l>=i)ans++;
l=r=sa[j];
}
}
if(r-l>=i)ans++;
}
printf("%d\n",ans);
}
return ;
}
hdu_3518_Boring counting(后缀数组)的更多相关文章
- hdu3518 Boring counting(后缀数组)
Boring counting 题目传送门 解题思路 后缀数组.枚举每种长度,对于每个字符串,记录其最大起始位置和最小起始位置,比较是否重合. 代码如下 #include <bits/stdc+ ...
- hdu 3518 Boring counting 后缀数组LCP
题目链接 题意:给定长度为n(n <= 1000)的只含小写字母的字符串,问字符串子串不重叠出现最少两次的不同子串个数; input: aaaa ababcabb aaaaaa # output ...
- hdu 3518 Boring counting 后缀数组基础题
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Total Submission( ...
- hdu 3518 Boring counting 后缀数组
题目链接 根据height数组的性质分组计算. #include <iostream> #include <vector> #include <cstdio> #i ...
- hdu 3518 Boring counting 后缀数组 height分组
题目链接 题意 对于给定的字符串,求有多少个 不重叠的子串 出现次数 \(\geq 2\). 思路 枚举子串长度 \(len\),以此作为分界值来对 \(height\) 值进行划分. 显然,对于每一 ...
- 后缀数组 --- HDU 3518 Boring counting
Boring counting Problem's Link: http://acm.hdu.edu.cn/showproblem.php?pid=3518 Mean: 给你一个字符串,求:至少出 ...
- Boring counting HDU - 3518 (后缀数组)
Boring counting \[ Time Limit: 1000 ms \quad Memory Limit: 32768 kB \] 题意 给出一个字符串,求出其中出现两次及以上的子串个数,要 ...
- HDU 3518 Boring counting(后缀数组,字符处理)
题目 参考自:http://blog.sina.com.cn/s/blog_64675f540100k9el.html 题目描述: 找出一个字符串中至少重复出现两次的字串的个数(重复出现时不能重叠). ...
- bnuoj 34990(后缀数组 或 hash+二分)
后缀数组倍增算法超时,听说用3DC可以勉强过,不愿写了,直接用hash+二分求出log(n)的时间查询两个字符串之间的任意两个位置的最长前缀. 我自己在想hash的时候一直在考虑hash成数值时MOD ...
随机推荐
- 关于Application的onCreate以及Activity生命周期在源码里都是什么时候调用的
在ActivityThread.handleLaunchActivity中 Activity a = performLaunchActivity(r, customIntent);这一方法最终回调目标 ...
- intellij idea 12 搭建maven web项目
原来公司一直使用eclipse,突然使用这个intellij还真有点不习惯,等用了一段时间才发现的确好用,因为也是刚开始用,所以很多不理解的地方,搭建一个项目从头好好了解下intellij 最开始的m ...
- Java知识总结
...
- 第六十七节,html表单元素
html表单元素 学习要点: 1.表单元素总汇 2.表单元素解析 本章主要探讨HTML5中表单元素,表单元素用于获取用户的输入数据. 一.表单元素总汇 HTML5的表单中,提供了各种可供用户输入的 ...
- Computation expressions and wrapper types
原文地址:http://fsharpforfunandprofit.com/posts/computation-expressions-wrapper-types/ 在上一篇中,我们介绍了“maybe ...
- linux命令readlink
readlink,从字面意思就可以看出来,输出符号链接值或者权威文件名. openwrt 下的readlink命令参数如下: root@hbg:/# readlink --helpBusyBox v ...
- Chapter 15_1 require函数
Lua提供了一个名为require的高层函数来加载模块,但这个函数只假设了关于模块的基本概念. 对于require而言,一个模块就是一段定义了一些值(函数或者包含函数的table)的代码. 为了加载一 ...
- 【笔记】虚拟机用Xshell登陆报错“ssh服务器拒绝了密码”解决方法
自己本地安装了VMware Workstation之后,创建虚拟机,一开始是可以用Xshell登陆的,几天后,重启了电脑以及虚拟机,发现无法登陆了,还没有输入密码就有如下报错信息 这时候开始排查原因, ...
- solr定时增量索引
当数据库的数据发生改变的时候,我们不想手动的去重新添加数据库的数据导solr索引库中,所以用到定时添加索引.增删改的数据.现在写的这些都是基于我之前做的一步步到这来的. 将solr/dist下的sol ...
- js 弹出 隐藏层和cookie
<script type="text/javascript"> function checkCookie(show_div, bg_div) { var smtstk ...