记录编号 |
428328 |
评测结果 |
AAAAAAAAAAAAAAAAAAAA |
题目名称 |
[51nod 1129] 字符串最大值 |
最终得分 |
100 |
用户昵称 |
CSU_Turkey |
是否通过 |
通过 |
代码语言 |
C++ |
运行时间 |
0.102 s |
提交时间 |
2017-07-25 13:27:35 |
内存使用 |
8.90 MiB |
显示代码纯文本
- #include<bits/stdc++.h>
- using namespace std;
- int f[1000005],g[1000005];
- char a[1000005];
- int main()
- {
- freopen("string_maxval.in","r",stdin);
- freopen("string_maxval.out","w",stdout);
- scanf("%s",a);
- int lena=strlen(a);
- for(int i=lena;i>=1;i--)
- a[i]=a[i-1];
- for(int i=2;i<=lena;i++)
- {
- int j=f[i-1];
- while(j&&a[j+1]!=a[i])
- j=f[j];
- if(a[j+1]==a[i])
- f[i]=j+1;
- else
- f[i]=0;
- }
- for(int i=1;i<=lena;i++)
- g[i]=1;
- int ma=-1;
- for(int i=lena;i>=1;i--)
- {
- g[f[i]]+=g[i];
- ma=max(ma,i*g[i]);
- }
- cout<<ma;
- return 0;
- }
- /*
- 递推式昨天还会今天突然就不会了....屡了半天,大概知道了吧,一个串每出现一次,
- 你的最长前缀就多出现一次(递推式初始全是1表示从第一位开始的那个(不是加2不然这个会被重复计算))
- 至于前缀的前缀,我们乍一看,应该加3次,但只加了2次,是不是就有错呢?事实上是没有的,我们可以
- 模拟一下这个过程,(ababababcabababababab),(我连自己都说服不了..)往前找的时候
- 会出现一种情况,(恰好是当时的前缀去掉除其前缀以外的剩余字母(只不过发生在字符串尾部而不是前面))
- 当时前缀的前缀成了现在的前缀,会给他加上那缺少的一次,如果像我给的样例那样
- 到达那个位置的时候前缀并不是当时前缀的前缀,也就不会给他加,那该怎么办,我们会发现一直找下去总会有
- 我所说的那种情况出现,而中间都是重复的(前缀的前缀重复使用(在相邻两个"前缀“中分别充当前缀和后缀)),
- 所以不需要额外加;
- */