题中要求:

$\sum_{1\leqslant i < j \leq n } Len(T_{i}) +Len(T_{j})-2LCP(T_{i},T_{j})$

公式左边的部分很好求,是一个常量,关键在于如何求取右边的 $2*LCP(T_{i},T_{j})$

在后缀自动机中,任意两个字符串所代表的节点在 $Parent$ 树中的公共祖先所代表的字符串一

定为两个字符串的最长公共后缀,

我们想求最长公共前缀,将字符串倒着插入即可.

一次考虑每个点作为公共祖先能贡献的值:

我们要使答案不重复,不遗漏的计算到. 即任意两个串的 LCP 必须只算一次.

可以一边更新每个点的 right 数组大小,一边计算该点父亲的贡献.

细节可以自己思考.

Code:

  1. #include <cstdio>
  2. #include <algorithm>
  3. #include <cstring>
  4. #define setIO(s) freopen(s".in","r",stdin)
  5. #define maxn 1000000
  6. #define N 30
  7. #define ll long long
  8. using namespace std;
  9. int last=1,tot=1,n;
  10. int ch[maxn][N],cnt[maxn],f[maxn],dis[maxn],rk[maxn];
  11. ll C[maxn],ans;
  12. char str[maxn];
  13. struct Suffix_Automaton{
  14. void ins(int c){
  15. int p=last,np=++tot; last=np; dis[np]=dis[p]+1;
  16. while(p&&!ch[p][c])ch[p][c]=np,p=f[p];
  17. if(!p) f[np]=1;
  18. else{
  19. int q=ch[p][c],nq;
  20. if(dis[q]==dis[p]+1) f[np]=q;
  21. else{
  22. nq=++tot;
  23. dis[nq]=dis[p]+1;
  24. memcpy(ch[nq],ch[q],sizeof(ch[q]));
  25. f[nq]=f[q],f[q]=f[np]=nq;
  26. while(p&&ch[p][c]==q) ch[p][c]=nq,p=f[p];
  27. }
  28. }
  29. cnt[last]=1;
  30. }
  31. }sam;
  32. int main(){
  33. //s//etIO("input");
  34. scanf("%s",str),n=strlen(str);
  35. for(int i=n-1;i>=0;--i) sam.ins(str[i]-'a');
  36. for(int i=1;i<=tot;++i) ++C[dis[i]];
  37. for(int i=1;i<=tot;++i) C[i]+=C[i-1];
  38. for(int i=1;i<=tot;++i) rk[C[dis[i]]--]=i;
  39. for(int i = 1;i <= n; ++i) ans += (long long)i * (n - 1);
  40. for(int i=tot;i>=1;--i){
  41. int p=rk[i];
  42. ans -= (long long)2 * dis[f[p]] * cnt[p] * cnt[f[p]];
  43. cnt[f[p]]+=cnt[p];
  44. }
  45. printf("%lld",ans);
  46. return 0;
  47. }

  

  

[AHOI2013]差异 后缀自动机_Parent树的更多相关文章

  1. BZOJ 3238: [Ahoi2013]差异 [后缀自动机]

    3238: [Ahoi2013]差异 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 2512  Solved: 1140[Submit][Status ...

  2. [Ahoi2013]差异(后缀自动机)

    /* 前面的那一坨是可以O1计算的 后面那个显然后缀数组单调栈比较好写??? 两个后缀的lcp长度相当于他们在后缀树上的lca的深度 那么我们就能够反向用后缀自动机构造出后缀树然后统计每个点作为lca ...

  3. 洛谷P4248 [AHOI2013]差异(后缀自动机求lcp之和)

    题目见此 题解:首先所有后缀都在最后一个np节点,然后他们都是从1号点出发沿一些字符边到达这个点的,所以下文称1号点为根节点,我们思考一下什么时候会产生lcp,显然是当他们从根节点开始一直跳相同节点的 ...

  4. BZOJ 3238 [Ahoi2013]差异 ——后缀自动机

    后缀自动机的parent树就是反串的后缀树. 所以只需要反向构建出后缀树,就可以乱搞了. #include <cstdio> #include <cstring> #inclu ...

  5. [bzoj3238][Ahoi2013]差异——后缀自动机

    Brief Description Algorithm Design 下面给出后缀自动机的一个性质: 两个子串的最长公共后缀,位于这两个串对应的状态在parent树上的lca状态上.并且最长公共后缀的 ...

  6. BZOJ 3238: [Ahoi2013]差异 后缀自动机 树形dp

    http://www.lydsy.com/JudgeOnline/problem.php?id=3238 就算是全局变量,也不要忘记,初始化(吐血). 长得一副lca样,没想到是个树形dp(小丫头还有 ...

  7. BZOJ.3238.[AHOI2013]差异(后缀自动机 树形DP/后缀数组 单调栈)

    题目链接 \(Description\) \(Solution\) len(Ti)+len(Tj)可以直接算出来,每个小于n的长度会被计算n-1次. \[\sum_{i=1}^n\sum_{j=i+1 ...

  8. BZOJ3238: [Ahoi2013]差异(后缀自动机)

    题意 题目链接 Sol 前面的可以直接算 然后原串翻转过来,这时候变成了求任意两个前缀的最长公共后缀,显然这个值应该是\(len[lca]\),求出\(siz\)乱搞一下 #include<bi ...

  9. BZOJ3413: 匹配(后缀自动机 线段树合并)

    题意 题目链接 Sol 神仙题Orz 后缀自动机 + 线段树合并... 首先可以转化一下模型(想不到qwq):问题可以转化为统计\(B\)中每个前缀在\(A\)中出现的次数.(画一画就出来了) 然后直 ...

随机推荐

  1. eclipse搭建golang for windows

    用惯了eclipse,所以.... golang windows开发环境 参考文档:http://golang.org/doc/install 1.下载go安装包http://code.google. ...

  2. 产品开发也要看阵容,APP开发只需五步变得靠谱

    最早认识的一个朋友是程序员,曾经到一家外包公司接单子,小外包公司经常遇到的问题就是和需求方谈产品功能.客户要做外包,对方让他一次性报价,但是客户连功能点自己都不清楚,这时朋友说还是按照具体功能点来做吧 ...

  3. Type system

    Type system[edit] Main articles: Data type, Type system, and Type safety A type system defines how a ...

  4. Parameter ‘brOrderNo’ not found

    org.apache.ibatis.binding.BindingException: Parameter 'brOrderNo' not found. Available parameters ar ...

  5. 队列Queue的get方法

    写了一段生产者消费者模型的代码: from time import sleep from random import randint, random from multiprocessing impo ...

  6. linux系统添加环境变量,node.js forever 守护进程添加环境变量

    1.node.js 守护进程组件 forever 安装 npm install forever -g 安装完成后截图: 2.安装完成后在控制台输入 forever 出现 -bash: forever: ...

  7. nmcli

    [root@web01 ~]# nmcli device status DEVICE TYPE STATE CONNECTION eth0 ethernet connected eth0 lo loo ...

  8. Linux之awk使用

    基本语法 $n :当前记录的第n个字段,比如n为1表示第一个字段,n为2表示第二个字段 $0:执行过程中当前行的文本内容 \t:制表符 \n:换行符 -F'[:#/]' : 定义三个分隔符,注意有-F ...

  9. Android开发进度03

    1,今日:目标:实现登录界面 2,昨天:实现第一个Android项目Helloworld 3,收获:会使用手机进行测试,会使用SQlite数据库 4,问题:创建项目时出错

  10. js-DOM操作基本知识