(p.s:
已经很久没有做过ACM的题目了,今天又试着搞了一下,结果折腾一下午,就弄出一道题
,写点东西总结一下)。
题目来源:
HihoCoder 1032
要求:
给定字符串s,计算其中的最长的回文子串的长度。所谓“回文串”就是将字符串倒置,仍然是原字符串的字串,例如:aba,abcba等。 题目的要求是计算给出字符串中最长的回文子串的长度。字符串长度的范围是:≤1000000。
解答:
这个题目可以用暴力枚举的方式去求解。但长度为N的字符串字串数据为2^n,直接枚举可能会超时。简单说说我的解法:
对于字串s中的某一个元素s[i],记以s[i]为中心的最长回文串为U(i),这里借用了数学里面“邻域”的概念。而U(i)的长度可以记为Length(i),可以利用一个数组将每一个i的对应length(i)的值计算出来。而计算某一个U(i)时,U(0)....U(i-1)是已知的,可以利用这些信息将计算简化。
下面的计算方式基于这样的事实:对于某一元素s[i],查找s[0].....s[i-1],找到一个元素s[j],使得:s[i]∈U(j)。记关于s[j]的对称点为s[sym],那么U(i)值一定和U(sym)有一定的关系。
下面是各种情况的讨论:下面各图中记s[sym]为sym_center、s[j]为mid_center、U(j)的左右边界分别为mid_left和mid_right、U(j)的左右边界分别为sym_left和sym_right。图中右边元素的下表大于左边元素:
(i) mid_left < sym_left, 此时U(sym_center)是U(mid_center)的子集,而s[i]和s[sym _center ]关于s[mid _center ]对称,因此,s[i]的情况和s[sym_center ]完全相同,即:U(i) = U(sym_center ), length(i) = length(sym_center)。如下图:

题目来源:
HihoCoder 1032
要求:
给定字符串s,计算其中的最长的回文子串的长度。所谓“回文串”就是将字符串倒置,仍然是原字符串的字串,例如:aba,abcba等。 题目的要求是计算给出字符串中最长的回文子串的长度。字符串长度的范围是:≤1000000。
解答:
这个题目可以用暴力枚举的方式去求解。但长度为N的字符串字串数据为2^n,直接枚举可能会超时。简单说说我的解法:
对于字串s中的某一个元素s[i],记以s[i]为中心的最长回文串为U(i),这里借用了数学里面“邻域”的概念。而U(i)的长度可以记为Length(i),可以利用一个数组将每一个i的对应length(i)的值计算出来。而计算某一个U(i)时,U(0)....U(i-1)是已知的,可以利用这些信息将计算简化。
下面的计算方式基于这样的事实:对于某一元素s[i],查找s[0].....s[i-1],找到一个元素s[j],使得:s[i]∈U(j)。记关于s[j]的对称点为s[sym],那么U(i)值一定和U(sym)有一定的关系。
下面是各种情况的讨论:下面各图中记s[sym]为sym_center、s[j]为mid_center、U(j)的左右边界分别为mid_left和mid_right、U(j)的左右边界分别为sym_left和sym_right。图中右边元素的下表大于左边元素:
(i) mid_left < sym_left, 此时U(sym_center)是U(mid_center)的子集,而s[i]和s[sym _center ]关于s[mid _center ]对称,因此,s[i]的情况和s[sym_center ]完全相同,即:U(i) = U(sym_center ), length(i) = length(sym_center)。如下图: