O(n)的复杂度求回文串:Manacher算法

定义一个回文值,字符串S是K重回文串,当且仅当S是回文串,且其长度为⌊N/2⌋的前缀和长度为⌊N/2⌋的后缀是K−1重回文串

现在给一个2*10^6长度的字符串,求其每个前缀的最大回文值之和。

设dp[i]为长度为i的前缀的最大回文值。

当长度为i的前缀的字符串是回文串的时候,有:dp[i]=dp[i/2]+1

若不是回文串 dp[i]=0

接下来就是怎么样快速的判断回文串了,推荐算法Manacher算法。

Manacher算法先对字符串进行修改 如 aba -> $#a#b#a#

那么该怎么用DP求?

显然一下几点是满足的:

如果某个前缀是回文串,该前缀的末端一定是字符#,(因为第一个符号是#)

故对于不是字符#的位置,它的dp值一定为0

如果最大延伸数组p[i]=i,即向左正好延伸到最左边,那么1~p[i]+i-1一定是一个回文前缀

若第i位是#号 : dp[mx]=dp[i]  其中mx=p[i]+i-1

对于不是#的情况 : dp[mx]=dp[i-1] 其中mx=p[i]+i-1

#include<bits/stdc++.h>
#define eps 1e-9
#define FOR(i,j,k) for(int i=j;i<=k;i++)
#define MAXN 4000005
#define MAXM 40005
#define INF 0x3fffffff
#define PB push_back
#define MP make_pair
#define X first
#define Y second
#define lc (k<<1)
#define rc ((k<<1)1)
using namespace std;
typedef long long LL;
int i,j,k,n,m,x,y,T,ans,big,cas,num,len;
bool flag; int p[MAXN],dp[MAXN];
char str[MAXN],s[MAXN]; void kp()
{
int i;
int mx = ;
int id;
for(i=n; str[i]!=; i++)//清除n后边多余的部分
str[i] = ; //没有这一句有问题。。就过不了ural1297,比如数据:ababa aba
for(i=; i<n; i++)
{
if( mx > i )
p[i] = min( p[*id-i], p[id]+id-i );
//因为是从左往右扫描的这里i>id, 2*id-i是i关于id的对称点,该对称点在id的左端
//p[id]+id是描述中的mx,即id向右延伸的端点位置
//显然向右延伸是可能超出mx的,所以要有下边的for循环
else
p[i] = ;
for(; str[i+p[i]] == str[i-p[i]]; p[i]++); if( p[i] + i > mx )//更新mx与id,因为mx是向右延伸的最大长度,所以实时更新
{
mx = p[i] + i;
id = i;
}
}
} void init()//处理字符串
{
int i, j, k;
str[] = '$';
str[] = '#';
for(i=; i<n; i++)
{
str[i*+] = s[i];
str[i*+] = '#';
}
n = n*+;
s[n] = ;
} int main()
{
scanf("%s",s);
n=strlen(s);
init();
kp();
for (i=;i<n;i++)
{
if (p[i]==i)
{
int mx=p[i]+i-;
if (str[i]!='#')
{
dp[mx]=max(dp[mx],dp[i-]+);
}else
dp[mx]=max(dp[mx],dp[i]+);
}
}
int sum=;
for (i=;i<n;i++) sum+=dp[i];
printf("%d\n",sum);
return ;
}

2015 UESTC Training for Search Algorithm & String - M - Palindromic String【Manacher回文串】的更多相关文章

  1. UESTC_Palindromic String 2015 UESTC Training for Search Algorithm & String<Problem M>

    M - Palindromic String Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 128000/128000KB (Java ...

  2. UESTC_韩爷的梦 2015 UESTC Training for Search Algorithm & String<Problem N>

    N - 韩爷的梦 Time Limit: 200/100MS (Java/Others)     Memory Limit: 1300/1300KB (Java/Others) Submit Stat ...

  3. UESTC_Ferris Wheel String 2015 UESTC Training for Search Algorithm & String<Problem L>

    L - Ferris Wheel String Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 43000/43000KB (Java/ ...

  4. UESTC_秋实大哥の恋爱物语 2015 UESTC Training for Search Algorithm & String<Problem K>

    K - 秋实大哥の恋爱物语 Time Limit: 5000/2000MS (Java/Others)     Memory Limit: 32000/32000KB (Java/Others) Su ...

  5. UESTC_Eight Puzzle 2015 UESTC Training for Search Algorithm & String<Problem F>

    F - Eight Puzzle Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) ...

  6. UESTC_吴队长征婚 2015 UESTC Training for Search Algorithm & String<Problem E>

    E - 吴队长征婚 Time Limit: 10000/4000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submi ...

  7. UESTC_基爷的中位数 2015 UESTC Training for Search Algorithm & String<Problem D>

    D - 基爷的中位数 Time Limit: 5000/3000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submi ...

  8. UESTC_基爷与加法等式 2015 UESTC Training for Search Algorithm & String<Problem C>

    C - 基爷与加法等式 Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Subm ...

  9. UESTC_邱老师降临小行星 2015 UESTC Training for Search Algorithm & String<Problem B>

    B - 邱老师降临小行星 Time Limit: 10000/5000MS (Java/Others)     Memory Limit: 65536/65535KB (Java/Others) Su ...

随机推荐

  1. jQuery在on绑定事件时,使用Function.prototype.bind上下文,只能用off(event)解绑函数,否则可能导致事件叠加

    因为一个bind函数,未解绑成功导致事件叠加,搞了一下午. keyup事件绑定: this.$document.on('keyup', this.keyUp.bind(this)); 原解绑函数: t ...

  2. STM32学习笔记——USART串口(向原子哥和火哥学习)

    一.USART简介 通用同步异步收发器(USART)提供了一种灵活的方法与使用工业标准NRZ异步串行数据格式的外部设备之间进行全双工数据交换.USART利用分数波特率发生器提供宽范围的波特率选择. S ...

  3. BZOJ 2572 高速公路

    Description Y901高速公路是一条重要的交通纽带,政府部门建设初期的投入以及使用期间的养护费用都不低,因此政府在这条高速公路上设立了许多收费站.Y901高速公路是一条由N-1段路以及N个收 ...

  4. struts2接收参数——域模型、DTO

    在开始介绍域模型之前我们要明白一点,为什么通过域模型我们可以把参数这么方便的在后台接收. 那是因为 通过参数拦截器(params interceptor)自动的把前台传过来的参数给域对象(domain ...

  5. COJ 0047 20702最大乘积

    20702最大乘积 难度级别:B: 运行时间限制:1000ms: 运行空间限制:51200KB: 代码长度限制:2000000B 试题描述 输入n个元素组成的序列s,你需要找出一个乘积最大的连续子序列 ...

  6. 「Poetize9」礼物运送

    3055: 礼物运送 Time Limit: 3 Sec  Memory Limit: 128 MBSubmit: 18  Solved: 12[Submit][Status] Description ...

  7. DateDiff 函数,用生日获得年龄

    一:截图 二:代码 using System; using System.Collections.Generic; using System.ComponentModel; using System. ...

  8. Listview加载更多是,恢复到原来的位置,如果不加特殊处理,总是跳转第一条

    1.记录listView滚动到的位置的坐标,然后利用listView.scrollTo精确的进行恢复 listView.setOnScrollListener(new OnScrollListener ...

  9. [Locked] One Edit Distance

    One Edit Distance Given two strings S and T, determine if they are both one edit distance apart. 分析: ...

  10. SRM 398(1-250pt)

    题意:有两个变量x和y,三种运算符+,*,-,组成等式"变量 运算符 变量 运算符 变量 运算符 变量",要求每个变量恰好出现两次,且等式的值为val的等式有多少个.注意不计算运算 ...