Best Reward HDU - 3613(Manacher)

原创 2018年04月17日 16:15:53

Best Reward HDU - 3613

题目链接:https://cn.vjudge.net/contest/163024#problem/S
题目大意:26个字母,每个都有一个权值,给定一字符串,将这个字符串分给成两部分,分割后的两部分,如果该部分是回文的话它的价值就是所有字母的权值和,否则就是0。

input

2
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
aba
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
acacac

output

1
6
题目分析:可以预处理一下,这个串在第i点分隔开之后是否是回文,然后用前缀和处理一下权值即可。

#include <bits/stdc++.h>
using namespace std;

const int maxn = 1e6 + 10;

int p[maxn], v[30], sum[maxn], cnt, len;
bool Left[maxn], Right[maxn];
char str[maxn], s[maxn];

void init()
{
    memset(p, 0, sizeof(p));
    int i;
    cnt = 0;
    str[cnt++] = '$';
    for(i = 0; i < len; i++)
    {
        str[cnt++] = '#';
        str[cnt++] = s[i];
    }
    str[cnt++] = '#';
    str[cnt] = '\0';
}

void manacher()
{
    init();
    int po = 0, maxr = 0;
    for(int i = 1; i < cnt; i++)
    {
        if(maxr > i) p[i] = min(p[po * 2 - i], maxr - i);
        else p[i] = 1;

        while(str[i + p[i]] == str[i - p[i]]) p[i]++;

        if(i + p[i] > maxr)
        {
            maxr = i + p[i];
            po = i;
        }
        if(p[i] == i) Left[i - 1] = true;
        if(p[i] + i  == cnt) Right[p[i] - 1] = true;
    }
}

int main()
{
    int t, i;
    scanf("%d", &t);
    while(t--)
    {
        for(i = 0; i < 26; i++)
            scanf("%d", &v[i]);

        scanf("%s", s);
        len = strlen(s);

        memset(sum, 0, sizeof(sum));
        memset(Left, false, sizeof(Left));
        memset(Right, false, sizeof(Right));
        sum[0] = v[s[0] - 'a'];
        for(i = 1; i < len; i++)
        {
            sum[i] = sum[i - 1] + v[s[i] - 'a'];
        }

        manacher();

        int ans = 0;
        for(i = 1; i < len; i++)
        {
            int tmp = 0;
            if(Left[i])
            {
                tmp += sum[i - 1];
            }
            if(Right[len - i])
            {
                tmp += sum[len - 1] - sum[i - 1];
            }

            ans = max(tmp, ans);

        }

        printf("%d\n", ans);
    }
}

弄不懂的地方是:

  if(p[i] == i) Left[i - 1] = true;
  if(p[i] + i  == cnt) Right[p[i] - 1] = true;

这两行代码。
举个例子:abaaba
处理之后的是这样的

位置:0 1 2 3 4 5 6 7 8 9 10 11 12 13
字符:$ # a # b # a # a #  b  #  a  #
p[i]:  1 2 1 4 1 2 7 2 1  4  1  2  1

p[4] = 4,这时left[3] = true; 它的意思是 前缀 aba是个回文串。因为p[4] = 4,说明在str[1~3]个字符与后边[5~7]个字符组成了回文(当然是加上了4个字符),因为这个字符串是加上了#的,所以p[4]=4,是说明一共有3 * 2 + 1个字符,对应回原来的就是i- 1;
right同理,只不过处理的是后缀。

hdu 3613 Best Reward(manacher算法)

Best Reward 题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=3613 解题思路: 题目大意: 字母表的26个字母都有一个价值,...
  • piaocoder
  • piaocoder
  • 2016-04-04 17:20:46
  • 730

hdu 3613 Best Reward

题目大意:小写字母组成的长n的串, 每种字母有一定的价值(可以为负), 要你分成切成两个串, 总价值为两个串价值和, 若是回文, 则串的价值为每个字母价值和, 否则为0。 问最大价值多少。 思路:...
  • wdcjdtc
  • wdcjdtc
  • 2014-05-21 14:43:07
  • 470

Hdu 3613 . Best Reward

Hdu 3613 . Best Reward Problem DescriptionAfter an uphill battle, General Li won a great victory. No...
  • liyizhixl
  • liyizhixl
  • 2018-03-14 22:49:05
  • 43

hdu3613---Best Reward

Best Reward Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others) To...
  • Guard_Mine
  • Guard_Mine
  • 2015-02-02 12:50:40
  • 732

HDU 3613 Manacher应用

点击打开链接 题意:上面的数字是26个字母的价值,接下来26个英文字母组成的字符串,将它分成两份,如果分后的串是回文串,则这个串的价值是这个串的所有字母的和,如果不是回文串则这个串价值为0 思路:...
  • Dan__ge
  • Dan__ge
  • 2016-04-19 11:15:49
  • 1702

HDU - 3613 Best Reward

Best RewardTime Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total ...
  • Lngxling
  • Lngxling
  • 2018-02-25 20:41:58
  • 33

hdu 3613 Best Reward (manacher)

http://acm.hdu.edu.cn/showproblem.php?pid=3613 Best Reward Problem Description After an uphill b...
  • w144215160044
  • w144215160044
  • 2015-10-03 17:43:06
  • 206

HDU 3613 Best Reward (manacher)

题意: N
  • lwt36
  • lwt36
  • 2015-11-03 22:13:33
  • 307

HDU 3613 Best Reward(manacher)

Best Reward Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others) To...
  • dml_96
  • dml_96
  • 2015-08-14 10:06:42
  • 241

HDU 3613 Best Reward Manacher

After an uphill battle, General Li won a great victory. Now the head of state decide to reward him w...
  • YCQ_Lancet
  • YCQ_Lancet
  • 2017-08-17 21:45:29
  • 104
收藏助手
不良信息举报
您举报文章:Best Reward HDU - 3613(Manacher)
举报原因:
原因补充:

(最多只允许输入30个字)