zoukankan      html  css  js  c++  java
  • hdu5421 Victor and String 回文树(前后插入)

    题目传送门

    题意:对一个字符串支持四种操作,前插入字符,后插入字符,询问本质不同的回文串数量和所有回文串的数量。

    思路:

      就是在普通回文树的基础上,维护suf(最长回文后缀)的同时再维护一个pre(最长回文前缀),即可完成以上操作。

    代码基本是学习巨佬yyb

    #pragma GCC optimize (2)
    #pragma G++ optimize (2)
    #pragma comment(linker, "/STACK:102400000,102400000")
    #include<bits/stdc++.h>
    #include<cstdio>
    #include<vector>
    #define rep(i,a,b) for(int i=a;i<=b;i++)
    #define dep(i,b,a) for(int i=b;i>=a;i--)
    #define clr(a,b) memset(a,b,sizeof(a))
    #define pb push_back
    #define pii pair<int,int >
    using namespace std;
    typedef long long ll;
    ll rd()
    {
        ll x=0,f=1;char ch=getchar();
        while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
        while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();}
        return x*f;
    }
    const int maxn=300010;
    int size[maxn];
    char s[maxn];
    int l,r,pre,suf,n; 
    ll ans;
    struct Palindromic_Tree
    {
        struct Node
        {
            int son[26];
            int ff,len,dep;
        }t[maxn];
        int last,tot;
        void init()
        {
            l=1e5,r=l-1;
            tot=0;
            clr(s,'');
            clr(t,0);
            t[++tot].len=-1;
            t[0].ff=t[1].ff=1;
        }
        void extend(int c,int n,int &last,int op)
        {
            int p=last;
            while(s[n-op*t[p].len-op]!=s[n])p=t[p].ff;
            if(!t[p].son[c])
            {
                int v=++tot,k=t[p].ff;
                t[v].len=t[p].len+2;
                while(s[n-op*t[k].len-op]!=s[n])k=t[k].ff;
                t[v].ff=t[k].son[c];    
                t[p].son[c]=v;
                t[v].dep=t[t[v].ff].dep+1;
            }
            last=t[p].son[c];
            ans+=t[last].dep;
            if(t[last].len==r-l+1)pre=suf=last; 
        }
    }a;
    int main(){
        while(cin>>n){
            a.init();
            ans=0;
            while(n--){
                int op=rd();
                if(op<=2){
                    char c=getchar();
                    if(op==1)s[--l]=c,a.extend(c-97,l,pre,-1);
                    else s[++r]=c,a.extend(c-97,r,suf,1);
                }else if(op==3)printf("%d
    ",a.tot-1);
                else printf("%lld
    ",ans);
            }
        }
    }
  • 相关阅读:
    EOJ 2743 Stock Exchange
    POJ-3468 A Simple Problem with Integers
    EOJ-1104 bitmap
    【转】旋转卡壳——凸多边形间对踵点对(定义)
    Ring 3层枚举进程的四种方法
    XX-Net项目,免费浏览谷歌的伟大项目
    浅析Java中的内存机制
    Ubuntu下eclipse中安装Scala插件
    注入(5)---导入表注入(HookINT)
    Linux下MySQL导入文件出错ERROR 1290 (HY000)
  • 原文地址:https://www.cnblogs.com/mountaink/p/11557000.html
Copyright © 2011-2022 走看看