3676: [Apio2014]回文串


Time Limit: 20 Sec  Memory Limit: 128 MB
Submit: 3396  Solved: 1568
[Submit][Status][Discuss]

Description


考虑一个只包含小写拉丁字母的字符串s。我们定义s的一个子串t的“出 
现值”为t在s中的出现次数乘以t的长度。请你求出s的所有回文子串中的最 
大出现值。

Input


输入只有一行,为一个只包含小写字母(a -z)的非空字符串s。

Output


输出一个整数,为逝查回文子串的最大出现值。

Sample Input


【样例输入l】

abacaba 

【样例输入2]

www 

Sample Output


【样例输出l】

 

【样例输出2]

 

HINT


一个串是回文的,当且仅当它从左到右读和从右到左读完全一样。

在第一个样例中,回文子串有7个:a,b,c,aba,aca,bacab,abacaba,其中:

● a出现4次,其出现值为4:1:1=4

● b出现2次,其出现值为2:1:1=2

● c出现1次,其出现值为l:1:l=l

● aba出现2次,其出现值为2:1:3=6

● aca出现1次,其出现值为1=1:3=3

●bacab出现1次,其出现值为1:1:5=5

● abacaba出现1次,其出现值为1:1:7=7

故最大回文子串出现值为7。

【数据规模与评分】

数据满足1≤字符串长度≤300000。

分析:


回文树眼题,但是我不会回文树QAQ

于是后缀自动机加manacher,构造出后缀自动机parent树后倍增每个点2^i能到达的点的dis值。
然后就可以做了。。。

AC代码:


# include <iostream>
# include <cstdio>
# include <cstring>
using namespace std;
const int N = 3e5 + ;
long long ans;
int ch[N << ][];
int dis[N << ],fa[N << ],w[N << ],cnt = ,len;
int que[N << ],p[N << ],dt,Log[],g[N << ][],Id[N];
char str[N],s[N << ];
int Sam(int c,int last)
{
int u = last,cur;
while(u && !ch[u][c])que[++que[]] = u,u = fa[u];
if(!u)
{
cur = ++cnt;fa[cur] = ;
while(que[])ch[que[que[]--]][c] = cur;
}
else
{
int v = ch[u][c];
if(dis[v] == dis[u] + )
{
cur = ++cnt;fa[cur] = v;
while(que[])ch[que[que[]--]][c] = cur;
}
else
{
int av = ++cnt;dis[av] = dis[u] + ;cur = ++cnt;
while(que[])ch[que[que[]--]][c] = cur;
memcpy(ch[av],ch[v],sizeof ch[v]);
fa[av] = fa[v];fa[v] = fa[cur] = av;
while(u && ch[u][c] == v)ch[u][c] = av,u = fa[u];
}
}
dis[cur] = dis[last] + ;
return cur;
}
void Manacher()
{
s[] = '$';s[dt = ] = '#';
for(int i = ;i <= len;i++)s[++dt] = str[i],s[++dt] = '#';
int mx = ,id = ;p[] = p[] = ;
for(int i = ;i < dt;i++)
{
p[i] = min(p[ * id - i],mx - i);
while(s[i + p[i] + ] == s[i - p[i] - ])
{
p[i]++;
if((i + p[i]) & )
{
int now = Id[(i + p[i] - ) >> ],L = ((i + p[i] - ) >> ) - ((i - p[i] + ) >> ) + ;
for(int j = ;~j;j--)if(dis[g[now][j]] >= L)now = g[now][j];
ans = max(ans,1LL * L * w[now]);
}
}
if(i + p[i] > mx)
{
id = i;
mx = i + p[i];
}
}
}
void init()
{
Log[] = ;for(int i = ;i < ;i++)Log[i] = Log[i - ] << ;
for(int i = ;i <= cnt;i++)g[i][] = fa[i];//这里考场上写成了<=len,结果得了90
for(int j = ;j <= ;j++)
for(int i = ;i <= cnt;i++)
g[i][j] = g[g[i][j - ]][j - ];
}
int main()
{
scanf("%s",str + );len = strlen(str + );Id[] = ;
for(int i = ;i <= len;i++)Id[i] = Sam(str[i] - 'a',Id[i - ]),w[Id[i]]++;
for(int i = ;i <= cnt;i++)p[dis[i]]++;
for(int i = ;i <= len;i++)p[i] += p[i - ];
for(int i = cnt;i >= ;i--)que[p[dis[i]]--] = i;
for(int i = cnt;i >= ;i--)w[fa[que[i]]] += w[que[i]];
init();Manacher();
printf("%lld\n",ans);
return ;
}

[Bzoj3676][Apio2014]回文串(后缀自动机)(parent树)(倍增)的更多相关文章

  1. bzoj3676 [Apio2014]回文串 卡常+SAM+树上倍增

    bzoj3676 [Apio2014]回文串 SAM+树上倍增 链接 bzoj luogu 思路 根据manacher可以知道,每次暴力扩展才有可能出现新的回文串. 所以推出本质不同的回文串个数是O( ...

  2. BZOJ 3676 [Apio2014]回文串 (后缀自动机+manacher/回文自动机)

    题目大意: 给你一个字符串,求其中回文子串的长度*出现次数的最大值 明明是PAM裸题我干嘛要用SAM做 回文子串有一个神奇的性质,一个字符串本质不同的回文子串个数是$O(n)$级别的 用$manach ...

  3. BZOJ 3676: [Apio2014]回文串 后缀自动机 Manacher 倍增

    http://www.lydsy.com/JudgeOnline/problem.php?id=3676 过程很艰难了,第一次提交Manacher忘了更新p数组,超时,第二次是倍增的第0维直接在自动机 ...

  4. [APIO2014]回文串 后缀自动机_Manancher_倍增

    Code: // luogu-judger-enable-o2 #include <cstdio> #include <algorithm> #include <cstr ...

  5. [模板] 回文树/回文自动机 &amp;&amp; BZOJ3676:[Apio2014]回文串

    回文树/回文自动机 放链接: 回文树或者回文自动机,及相关例题 - F.W.Nietzsche - 博客园 状态数的线性证明 并没有看懂上面的证明,所以自己脑补了一个... 引理: 每一个回文串都是字 ...

  6. [BZOJ3676][APIO2014]回文串(Manacher+SAM)

    3676: [Apio2014]回文串 Time Limit: 20 Sec  Memory Limit: 128 MBSubmit: 3097  Solved: 1408[Submit][Statu ...

  7. BZOJ3676 APIO2014回文串(manacher+后缀自动机)

    由于本质不同的回文子串数量是O(n)的,考虑在对于每个回文子串在第一次找到它时对其暴力统计.可以发现manacher时若右端点移动则找到了一个新回文串.注意这样会漏掉串长为1的情况,特判一下. 现在问 ...

  8. 2018.12.15 bzoj3676: [Apio2014]回文串(后缀自动机)

    传送门 对原串建立一个后缀自动机,然后用反串在上面匹配. 如果当前匹配的区间[l,r][l,r][l,r]包裹了当前状态的endposendposendpos中的最大值,那么[l,maxpos][l, ...

  9. [bzoj3676][Apio2014]回文串——Manacher+后缀自动机+倍增

    Brief Description 一个回文串的value定义为这个回文串的长度乘以出现次数.给定一个字符串,求\(value_{max}\). Algorithm Design 我们使用Manach ...

随机推荐

  1. 正则匹配闭合HTML标签(支持嵌套)

    任何复杂的正则表达式都是由简单的子表达式组成的,要想写出复杂的正则来,一方面需要有化繁为简的功底,另外一方面,我们需要从正则引擎的角度去思考问题.关于正则引擎的原理,推荐<Mastering R ...

  2. AEAI DP开发平台精要

    1 背景概述 相信很多了解数通畅联软件的人对AEAI DP应用开发平台并不陌生,笔者在入职第一天就开始接触AEAI DP,使用AEAI DP开发过AEAI WM.AEAI CRM以及中国XXXX管理系 ...

  3. MySQL &#183; 性能优化&#183; InnoDB buffer pool flush策略漫谈

    MySQL · 性能优化· InnoDB buffer pool flush策略漫谈 背景 我们知道InnoDB使用buffer pool来缓存从磁盘读取到内存的数据页.buffer pool通常由数 ...

  4. 关于python的import

    在软件包里,必须添加__init__.py文件. 想要对外公开的module必须在__init__.py内import一次,这样这些module才能被外部代码import并调用.

  5. poj 2454 Jersey Politics 随机化

    随机化算法+贪心! 将3*k排序后分成3分,将第二第三份的和分别加起来,让和与500*k比较,都大于则输出,否则,随机生成2个数,在第二第三份中交换! 代码如下: #include<iostre ...

  6. php开发环境配置 web UI模板

    web ui 能快速的整合进来?dwz? easyui?  bootstrap 在Apache 中配置: 在http.conf中加入php的设置 #php5_startphpIniDir " ...

  7. 使用 Git 同步时出现ssl错误

    错误提示 fatal: unable to access 'https://android.googlesource.com/platform/prebuilts/qemu-kernel/': gnu ...

  8. Linux进程管理:查杀进程

    一.查看进程 Linux下显示系统进程的命令ps,最常用的有ps -ef 和ps aux.这两个到底有什么区别呢? 两者没太大差别,讨论这个问题,要追溯到Unix系统中的两种风格,System V风格 ...

  9. 什么是 B 树?

    本文提到的「B-树」,就是「B树」,都是 B-tree 的翻译,里面不是减号-,是连接符-.因为有人把 B-tree 翻成 「B-树」,让人以为「B树」和「B-树」是两种树,实际上两者就是同一种树. ...

  10. python设计模式第二十天【迭代器模式】

    1.不使用迭代器出现的问题 (1)容器承担了太多的功能,一方面提供添加和删除等功能,还需提供遍历访问功能 (2)在容器访问遍历过程中,需要保存遍历状态,当和元素的添加和删除混杂在一起时,容易引起混乱 ...