码迷,mamicode.com
首页 > 其他好文 > 详细

回文树入门

时间:2018-09-06 14:39:50      阅读:344      评论:0      收藏:0      [点我收藏+]

标签:组成   problem   oid   lin   回文   target   ast   tps   freopen   

 

回文串  HYSBZ - 3676

考虑一个只包含小写拉丁字母的字符串s。我们定义s的一个子串t的“出 
现值”为t在s中的出现次数乘以t的长度。请你求出s的所有回文子串中的最 
大出现值。 

 

建一颗回文树,然后getans统计答案就OK了.  (回文树见IOI2017论文)

#include <cstdio>

const int maxn = 300050;

class pal {
public:
    int next[maxn][26];
    int fail[maxn];
    int len[maxn];
    int cnt[maxn];
    char str[maxn];
    int last;
    int tot;
    int n;
    
    // 记录节点长度,同时返回一个节点 
    inline int node(int _len) {
        len[tot] = _len;
        return tot++;
    }
    
    // odd根初始化为: 长度为-1  even根初始化len为0
    // 同时str[0]设置为字符集没有的字符 用于判断.
    // even根的fail指针是odd根 odd根的fail指针是自身. 
    void init() {
        last = tot = n = 0;
        node(0); node(-1);
        str[0] = -1;  fail[0] = fail[1] = 1; 
    }
    
    // 获得添加字符后,可以组成回文串的位置. 
    inline int GetFail(int cur) {
        while (str[n-len[cur]-1] != str[n])
            cur = fail[cur];
        return cur;
    }
    
    // 添加新字符  
    void insert(char ch) {
        str[++n] = ch;  
        int cur = GetFail(last), now;
        if (!next[cur][ch]) {
            now = node(len[cur] + 2);
            fail[now] = next[GetFail(fail[cur])][ch]; //和下一句的顺序不能反 
            next[cur][ch] = now;
        }
        ++cnt[last = next[cur][ch]]; // 出现次数,但是不完全统计,还需要for来统计.(因为一个长的回文串可能会包含一些小的回文串.) 
    }
    
    long long getans() {
        int i;
        long long res = 0;
        for (i=tot-1; i; --i)      //  统计出现次数 
            cnt[fail[i]] += cnt[i];
        for (i=tot-1; i; --i) 
            if (res < 1ll*len[i]*cnt[i])
                res = 1ll*len[i]*cnt[i];
        return res;        
    }
}pal;


char s[300050];

int main() {
//    freopen("E:\\input.txt", "r", stdin);
    pal.init();
    scanf("%s", s);
    for (char *p=s; *p; p++) 
        pal.insert(*p - a);
    printf("%lld\n", pal.getans());
    return 0;
}

 

回文树入门

标签:组成   problem   oid   lin   回文   target   ast   tps   freopen   

原文地址:https://www.cnblogs.com/cgjh/p/9597551.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!