题目链接


\(Description\)

给定一棵\(Trie\)。求\(Trie\)上所有回文串 长度乘以出现次数 的和。这里的回文串只能是从上到下的一条链。

节点数\(n\leq 2\times 10^6\),字符集为a,b,c,d

\(Solution\)

如果不是树,就是回文树模板。对于树,DFS \(x\)的每个儿子的时候都用在\(x\)处的\(las\)即可,也就是按深度存一个\(las\)数组,每次用\(las[dep-1]\)做\(las\)去插入即可。(也可以回溯的时候直接删节点)

每次插入产生的贡献怎么算。。?

令\(ans[x]\)表示\(x\)节点(状态)处的贡献,插入后到了\(x\)节点答案就加上\(ans[x]\)。

对于新建的\(x\)节点,\(ans[x]=len[x]+ans[fail[x]]\)(除了新产生的串,剩下的贡献就是\(fail[x]\)的状态的贡献了)。

加了fread之后惊呆了= =拿到了hdu上第一个rank1= =

果然不是我算法效率问题。。。



话说我为什么不需要开栈啊


//1092MS	151236K(fread) <- 7784MS	149280K
#include <cstdio>
#include <cctype>
#include <cstring>
#include <algorithm>
//#define gc() getchar()
#define MAXIN 2000000
#define gc() (SS==TT&&(TT=(SS=IN)+fread(IN,1,MAXIN,stdin),SS==TT)?EOF:*SS++)
typedef long long LL;
const int N=2e6+6; char IN[MAXIN],*SS=IN,*TT=IN; inline int read()
{
int now=0;register char c=gc();
for(;!isdigit(c);c=gc());
for(;isdigit(c);now=now*10+c-48,c=gc());
return now;
} struct PAM
{
int s[N],H[N],nxt[N],tot,las[N],son[N][4],len[N],fail[N];
LL Ans,ans[N];
char tmp[N];
inline void Init()
{
las[0]=tot=1, fail[0]=1, len[1]=-1, s[0]=-1;
memset(son[0],0,sizeof son[0]), memset(son[1],0,sizeof son[1]);
}
inline int Find(int x,int n)
{
while(s[n]!=s[n-len[x]-1]) x=fail[x];
return x;
}
void Insert(int c,int n)
{
s[n]=c;
int p=Find(las[n-1],n);
if(!son[p][c])
{
int np=++tot;
memset(son[np],0,sizeof son[np]);
fail[np]=son[Find(fail[p],n)][c];
son[p][c]=np, len[np]=len[p]+2;
ans[np]=ans[fail[np]]+len[np];
}
Ans+=ans[las[n]=son[p][c]];
}
void DFS(int x,int dep)
{
for(int v=H[x]; v; v=nxt[v])
Insert(tmp[v]-'a',dep), DFS(v,dep+1);
}
void Solve()
{
Init();
const int n=read();
for(int i=1; i<=n; ++i)
{
while(!isalpha(tmp[i]=gc()));
int fa=read();
nxt[i]=H[fa], H[fa]=i;
}
Ans=0, DFS(0,1), printf("%lld\n",Ans);
memset(H,0,n+1<<2);
}
}pam; int main()
{
for(int T=read(); T--; pam.Solve());
return 0;
}

HDU.5394.Trie in Tina Town(回文树)的更多相关文章

  1. HDU 5421 Victor and String(回文树)

    Victor and String Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 524288/262144 K (Java/Othe ...

  2. HDU 5157 Harry and magic string(回文树)

    Harry and magic string Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/O ...

  3. HDU 5658 CA Loves Palindromic(回文树)

    CA Loves Palindromic Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 262144/262144 K (Java/O ...

  4. HDU 6599 I Love Palindrome String (回文树+hash)

    题意 找如下子串的个数: (l,r)是回文串,并且(l,(l+r)/2)也是回文串 思路 本来写了个回文树+dfs+hash,由于用了map所以T了 后来发现既然该子串和该子串的前半部分都是回文串,所 ...

  5. HDU - 5421:Victor and String (回文树,支持首尾插入新字符)

    Sample Input 6 1 a 1 b 2 a 2 c 3 4 8 1 a 2 a 2 a 1 a 3 1 b 3 4 Sample Output 4 5 4 5 11 题意:多组输入,开始字符 ...

  6. HDU - 5157 :Harry and magic string (回文树,求多少对不相交的回文串)

    Sample Input aca aaaa Sample Output 3 15 题意: 多组输入,每次给定字符串S(|S|<1e5),求多少对不相交的回文串. 思路:可以用回文树求出以每个位置 ...

  7. Victor and String HDU - 5421 双向回文树

    题意: 有n种操作,开始给你一个空串,给你4中操作 1 c  在字符串的首部添加字符c 2 c  在字符串的尾部添加字符c 3  询问字符中的本质不同的回文串的个数 4 询问字符串中回文串的个数 思路 ...

  8. Interesting HDU - 5785 回文树

    题意: 找出所有[i,j]为回文串[j+1,k]也为回文串的i*k乘积之和. 题解: 设sum1[i] 为正着插入,到 i 的所有回文串的起始位置的前缀和,sum2[i] 表示反正插入的前缀和 ans ...

  9. 杭电多校HDU 6599 I Love Palindrome String (回文树)题解

    题意: 定义一个串为\(super\)回文串为: \(\bullet\) 串s为主串str的一个子串,即\(s = str_lstr_{l + 1} \cdots str_r\) \(\bullet\ ...

随机推荐

  1. vue和stylus在subline中显示高亮

    首先: 安装这两个插件   Vue Syntax Highlight    和    stylus 1.按住 ctrl + shift + p 2.输入:install Package 3.输入: V ...

  2. 【C++ Primer | 07】常用算法

    第一部分 常用泛型算法: find(beg, end, val); equal(beg1, end1, beg2); fill(beg, end, val); fill_n(beg, cnt, val ...

  3. MyBatis - 2.全局文件配置

    1.properties 属性 <!--properties 引入外部配置文件 properties 的内容 resource: 引入类路径资源 url: 引入网络资源 --> <p ...

  4. [转] css3变形属性transform

    w3c上的例子是这样子写的:· div { transform:rotate(7deg); -ms-transform:rotate(7deg); /* IE 9 */ -moz-transform: ...

  5. 次小生成树(POJ1679/CDOJ1959)

    POJ1679 首先求出最小生成树,记录权值之和为MinST.然后枚举添加边(u,v),加上后必形成一个环,找到环上非(u,v)边的权值最大的边,把它删除,计算当前生成树的权值之和,取所有枚举加边后生 ...

  6. Java集合源码学习(二)ArrayList

    1.关于ArrayList ArrayList直接继承AbstractList,实现了List. RandomAccess.Cloneable.Serializable接口,为什么叫"Arr ...

  7. bzoj2961 共点圆 bzoj 4140

    题解: 比较水的一道题 首先我们化简一下式子发现是维护xxo+yyo的最值 显然是用凸包来做 我们可以直接用支持插入删除的凸包 也是nlogn的 因为没有强制在线,我们也可以cdq,考虑前面一半对答案 ...

  8. 将input或textarea设置为disabled的样式问题

    input:disabled{ -webkit-text-fill-color: #333;//是用来做填充色使用的 -webkit-opacity: 1; color: #333; } textar ...

  9. Codeforces 609F Frogs and mosquitoes 线段树

    Frogs and mosquitoes 用线段树维护每个点覆盖的最小id, 用multiset维护没有吃的蚊子. #include<bits/stdc++.h> #define LL l ...

  10. Codeforces 1000G Two-Paths 树形动态规划 LCA

    原文链接https://www.cnblogs.com/zhouzhendong/p/9246484.html 题目传送门 - Codeforces 1000G Two-Paths 题意 给定一棵有 ...