Manacher(最长镜面回文串)

I - O'My!

Gym - 101350I

Note: this is a harder version of Mirrored string I.

The gorillas have recently discovered that the image on the surface of the water is actually a reflection of themselves. So, the next thing for them to discover is mirrored strings.

A mirrored string is a palindrome string that will not change if you view it on a mirror.

Examples of mirrored strings are "MOM", "IOI" or "HUH". Therefore, mirrored strings must contain only mirrored letters {A, H, I, M, O, T, U, V, W, X, Y} and be a palindrome.

e.g. IWWI, MHHM are mirrored strings, while IWIW, TFC are not.

A palindrome is a string that is read the same forwards and backwards.

Given a string S of length N, help the gorillas by printing the length of the longest mirrored substring that can be made from string S.

A substring is a (possibly empty) string of characters that is contained in another string S. e.g. "Hell" is a substring of "Hello".


Input

The first line of input is T – the number of test cases.

Each test case contains a non-empty string S of maximum length 1000. The string contains only uppercase English letters.

Output

For each test case, output on a line a single integer - the length of the longest mirrored substring that can be made from string S.

Example
Input
3
IOIKIOOI
ROQ
WOWMAN
Output
4
1
3
思路:将镜面字母拆分出来,一个一个求最长回文串,差点因为数组重复而runtime error 没过,还好发现了
#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <iostream>
#include<cstdio>
#include<string>
#include<cstring>
#include <stdio.h>
#include <string.h>
using namespace std;
const int N = 1000009 ;
char a[10009] , b[20009] ;
int p[20009] ;
int vis[27] ;
char c[20] = {'A', 'H', 'I', 'M', 'O', 'T', 'U', 'V', 'W', 'X', 'Y'};
char d[10009] ;

int cal(char *a , int lena)
{
        b[0] = '$';
        b[1] = '#';
        int l = 2 ;
        for(int i = 0 ; i < lena ; i++)
        {
            b[l++] = a[i];
            b[l++] = '#';
        }
        b[l] = '\0';
    //    cout << b << endl ;
        int mx = -1 ;
        int mid , i ;
        int len = 0 ;
        for(int i = 1 ; i < l ; i++)
        {
                if(mx > i)
                {
                    p[i] = min(p[mid * 2 - i] , mx - i);
                }
                else
                {
                    p[i] = 1 ;
                }
                while(b[i-p[i]] == b[i+p[i]])
                {
                     p[i]++;
                }
                if(mx < p[i] + i)
                {
                    mid = i ;
                    mx = p[i] + i ;
                }
                len = max(len , p[i] - 1);

        }
        return len ;
}

int main()
{
    for(int i = 0 ; i < 11 ; i++)
    {
        int x = c[i] - 'A';
        vis[x] = 1 ;
    }
    int n ;
    scanf("%d" , &n);
    while(n--)
    {

        scanf("%s" , a);
        int lena = strlen(a);
        int ans = 0 ;
        int l = 0 ;
        for(int i = 0 ; i < lena ; i++)
        {
            if(vis[a[i] - 'A'])
            {
                d[l++] = a[i];
            }
            if(!vis[a[i] - 'A'] || i == lena - 1)
            {

                if(l >= 1)
                    ans = max(ans ,cal(d , l));
                d[l] = 0 ;
                l = 0 ;
                continue ;
            }
        }
        printf("%d\n" , ans);
    }



    return 0 ;
}

猜你喜欢

转载自www.cnblogs.com/nonames/p/11291334.html
今日推荐