zoukankan      html  css  js  c++  java
  • Luogu3804 【模板】后缀自动机(后缀自动机)

      建出parent树统计即可。开始memcpy处写的是sizeof(son[y]),然后就T掉了……还是少用这种东西吧。

      同时也有SA做法。答案子串一定是名次数组中相邻两个串的lcp。单调栈统计其是几个后缀的前缀即可。

    #include<iostream> 
    #include<cstdio>
    #include<cmath>
    #include<cstdlib>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    int read()
    {
        int x=0,f=1;char c=getchar();
        while (c<'0'||c>'9') {if (c=='-') f=-1;c=getchar();}
        while (c>='0'&&c<='9') x=(x<<1)+(x<<3)+(c^48),c=getchar();
        return x*f;
    }
    #define N 2000010
    int n,cnt,last,son[N][26],fail[N],size[N],len[N],t=0,p[N];
    struct data{int to,nxt;
    }edge[N];
    void ins(int c) 
    {
        int x=++cnt,p=last;last=x;len[x]=n;size[x]=1;
        while (!son[p][c]&&p) son[p][c]=x,p=fail[p];
        if (!p) fail[x]=1;
        else
        {
            int q=son[p][c];
            if (len[q]==len[p]+1) fail[x]=q;
            else
            {
                int y=++cnt;
                len[y]=len[p]+1;
                memcpy(son[y],son[q],sizeof(son[q]));
                fail[y]=fail[q],fail[x]=fail[q]=y;
                while (son[p][c]==q) son[p][c]=y,p=fail[p];
            }
        }
    }
    void addedge(int x,int y){t++;edge[t].to=y,edge[t].nxt=p[x],p[x]=t;}
    void dfs(int k)
    {
        for (int i=p[k];i;i=edge[i].nxt) 
        {
            dfs(edge[i].to);
            size[k]+=size[edge[i].to];
        }
    }
    int main()
    {
    #ifndef ONLINE_JUDGE
        freopen("suffixautomaton.in","r",stdin);
        freopen("suffixautomaton.out","w",stdout);
        const char LL[]="%I64d
    ";
    #else
        const char LL[]="%lld
    ";
    #endif
        last=cnt=1;
        char c=getchar();
        while (c>='a'&&c<='z') n++,ins(c-97),c=getchar();
        for (int i=2;i<=cnt;i++) addedge(fail[i],i);
        dfs(1);
        long long ans=0;
        for (int i=1;i<=cnt;i++)
        if (size[i]>1) ans=max(ans,1ll*size[i]*len[i]);
        cout<<ans;
        return 0;
    }
  • 相关阅读:
    剑指 Offer 50. 第一个只出现一次的字符
    剑指 Offer 42. 连续子数组的最大和
    剑指 Offer 41. 数据流中的中位数
    剑指 Offer 40. 最小的k个数
    剑指 Offer 39. 数组中出现次数超过一半的数字
    剑指 Offer 38. 字符串的排列
    MySQL更改密码
    WPF中的MySQLHelper
    WPF多线程
    mysql-5.7.28-winx64(压缩包)安装教程
  • 原文地址:https://www.cnblogs.com/Gloid/p/9523511.html
Copyright © 2011-2022 走看看