题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3613

题目大意:

题目大意就是将字符串s分成两部分子串,
若子串是回文串则需计算价值,否则价值为0,求分割字符串s能获得的最大价值。

解题思路:

用manacher算法计算出p[i],每次计算p[i]是顺便计算一下这段回文串
是否能到达边界,若能则计算出前缀或者后缀的结束位置,标记起来。//还有之前数组开1e6+5教C++是错的,改成2e6+5就对了,不觉明历。。。。

代码(复杂点的)

 #include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int N=2e6+;
const int INF=0x3f3f3f3f; int len1,len2;
int p[N],sum[N],val[N],pre[N],hou[N];
char s[N],str[N]; void init(){
str[]='$';
str[]='#';
for(int i=;i<len1;i++){
str[i*+]=s[i];
str[i*+]='#';
}
len2=len1*+;
str[len2]='\0';
} void manacher(){
int id=,mx=;
for(int i=;i<len2;i++){
if(mx>i) p[i]=min(p[*id-i],mx-i);
else p[i]=;
while(str[i+p[i]]==str[i-p[i]])
p[i]++;
if(p[i]+i>mx){
id=i;
mx=p[i]+i;
}
if(i-p[i]==){
pre[p[i]+i-]=;
}
if(i+p[i]==len2){
hou[i-p[i]+]=;
}
}
} int main(){
int t;
scanf("%d",&t);
while(t--){
memset(pre,,sizeof(pre));
memset(hou,,sizeof(hou));
for(int i=;i<;i++){
scanf("%d",&val[i]);
}
scanf("%s",s);
len1=strlen(s);
init();
manacher();
for(int i=;i<len2;i++){
if(i=='#') sum[i]=sum[i-];
else sum[i]=sum[i-]+val[str[i]-'a'];
}
int ans=-INF;
//枚举分割点
for(int i=;i<len2-;i++){
int tmp=;
if(pre[i]) tmp+=sum[i];
if(hou[i]) tmp+=sum[len2-]-sum[i];
ans=max(ans,tmp);
}
printf("%d\n",ans);
}
return ;
}

简略了一点的

 #include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int N=2e6+;
const int INF=0x3f3f3f3f; int len1,len2;
int p[N],sum[N],val[N];
char s[N],str[N]; void init(){
str[]='$';
str[]='#';
for(int i=;i<len1;i++){
str[i*+]=s[i];
str[i*+]='#';
}
len2=len1*+;
str[len2]='@';
} void manacher(){
int id=,mx=;
for(int i=;i<len2;i++){
if(mx>i) p[i]=min(p[*id-i],mx-i);
else p[i]=;
while(str[i+p[i]]==str[i-p[i]])
p[i]++;
if(p[i]+i>mx){
id=i;
mx=p[i]+i;
}
}
} int main(){
int t;
scanf("%d",&t);
while(t--){
for(int i=;i<;i++){
scanf("%d",&val[i]);
}
scanf("%s",s);
len1=strlen(s);
init();
manacher();
for(int i=;i<len2;i++){
if(i=='#') sum[i]=sum[i-];
else sum[i]=sum[i-]+val[str[i]-'a'];
}
int ans=-INF;
//枚举分割点
for(int i=;i<len1-;i++){
int tmp=,mid;
mid=((i+)*++)/;
if(mid-p[mid]==) tmp+=sum[(i+)*];
mid=((i+)*-+len1*+)/;
if(mid+p[mid]==len2) tmp+=sum[len2-]-sum[(i+)*-];
ans=max(tmp,ans);
}
printf("%d\n",ans);
}
return ;
}

HDU 3613 Best Reward(manacher求前、后缀回文串)的更多相关文章

  1. POJ 3376 Finding Palindromes(manacher求前后缀回文串+trie)

    题目链接:http://poj.org/problem?id=3376 题目大意:给你n个字符串,这n个字符串可以两两组合形成n*n个字符串,求这些字符串中有几个是回文串. 解题思路:思路参考了这里: ...

  2. HDU 3613 Best Reward(扩展KMP求前后缀回文串)

    题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=3613 题目大意: 大意就是将字符串s分成两部分子串,若子串是回文串则需计算价值,否则价值为0,求分割 ...

  3. Manacher算法 - 求最长回文串的利器

    求最长回文串的利器 - Manacher算法 Manacher主要是用来求某个字符串的最长回文子串. 不要被manacher这个名字吓倒了,其实manacher算法很简单,也很容易理解,程序短,时间复 ...

  4. Manacher(最长镜面回文串)

    I - O'My! Gym - 101350I Note: this is a harder version of Mirrored string I. The gorillas have recen ...

  5. HDU 3613 Best Reward(KMP算法求解一个串的前、后缀回文串标记数组)

    题目链接: https://cn.vjudge.net/problem/HDU-3613 After an uphill battle, General Li won a great victory. ...

  6. hdu 3613"Best Reward"(Manacher算法)

    传送门 题意: 国王为了犒劳立下战功的大将军Li,决定奖给Li一串项链,这个项链一共包含26中珠子"a~z",每种珠子都有 相应的价值(-100~100),当某个项链可以构成回文时 ...

  7. hdu 3068 最长回文 【Manacher求最长回文子串,模板题】

    欢迎关注__Xiong的博客: http://blog.csdn.net/acmore_xiong?viewmode=list 最长回文                                 ...

  8. hdu 3068 最长回文 (Manacher算法求最长回文串)

    参考博客:Manacher算法--O(n)回文子串算法 - xuanflyer - 博客频道 - CSDN.NET 从队友那里听来的一个算法,O(N)求得每个中心延伸的回文长度.这个算法好像比较偏门, ...

  9. Manacher's Algorithm 马拉车算法(求最长回文串)

    作用:求一个字符串中的最长子串,同时还可以求所有子串的长度. 题目链接: https://vjudge.net/contest/254692#problem/B 最长回文串长度的代码: int Man ...

随机推荐

  1. bzoj2758【scoi2012】Blinker的的噩梦

    题目描述 一天Blinker醒来,发现自己成为了一个二维世界的点,而且被标记上了一个奇怪的值. 这个世界是由N个边界互不相交(且不相切)的图形组成,这里图形仅包括圆和凸多边形.每个图形还有一个权值.每 ...

  2. 【agc001d】Arrays and Palindrome

    Portal -->agc001D Description 给你一个\(m\)个数的排列\(A\),这个\(A\)中元素的顺序可以随便调换,\(A\)中的元素的和为\(n\),现在要你构造一个数 ...

  3. 《剑指offer》— JavaScript(24)二叉树中和为某一值的路径

    二叉树中和为某一值的路径 题目描述 输入一颗二叉树和一个整数,打印出二叉树中结点值的和为输入整数的所有路径.路径定义为从树的根结点开始往下一直到叶结点所经过的结点形成一条路径. 思路 前序遍历二叉树, ...

  4. GO_06:GO语言基础之struct

    结构struct 1. Go 中的struct与C中的struct非常相似,并且Go没有class 2. 使用 type <Name> struct{} 定义结构,名称遵循可见性规则(即首 ...

  5. pthread动态库命名规则

    Library naming-------------- Because the library is being built using various exceptionhandling sche ...

  6. Codeforces Round #477 (rated, Div. 2, based on VK Cup 2018 Round 3) D 贪心

    http://codeforces.com/contest/967/problem/D 题目大意: 有n个服务器,标号为1~n,每个服务器有C[i]个资源.现在,有两个任务需要同时进行,令他为x1,x ...

  7. 动态规划:POJ 3616 Milking Time

    #include <iostream> #include <algorithm> #include <cstring> #include <cstdio> ...

  8. Windows服务的安装和卸载

    ## install %SystemRoot%\Microsoft.NET\Framework\v4.0.30319\InstallUtil.exe ***Cache.WinService.exe # ...

  9. Redis实战(一)CentOS 7上搭建redis-3.0.2

    1.安装redis wget http://download.redis.io/releases/redis-3.0.2.tar.gz tar zxvf redis-3.0.2.tar.gz cd   ...

  10. c++刷题(9/100):链表

    题目一:https://www.nowcoder.com/practice/d0267f7f55b3412ba93bd35cfa8e8035?tpId=13&tqId=11156&tP ...