链接:http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=3587

题意:给出两个字符串S和T。S,T<=100000.拿出S的两个子串(能够重叠),将两个子串连接起来成为字符串T的方法有多少种。

思路:用扩展KMP求出S的从每位開始的子串与T的公共前缀,再将两个子串翻转,再用扩展KMP求出S反的从每位開始的子串与T反的公共前缀。找出当中和为T子串长度的S公共前缀和S反的公共前缀的数量,相乘为结果。

代码:

  1. #include <algorithm>
  2. #include <cmath>
  3. #include <cstdio>
  4. #include <cstdlib>
  5. #include <cstring>
  6. #include <ctime>
  7. #include <ctype.h>
  8. #include <iostream>
  9. #include <map>
  10. #include <queue>
  11. #include <set>
  12. #include <stack>
  13. #include <string>
  14. #include <vector>
  15. #define eps 1e-8
  16. #define INF 0x7fffffff
  17. #define maxn 10005
  18. #define PI acos(-1.0)
  19. #define seed 31//131,1313
  20. typedef long long LL;
  21. typedef unsigned long long ULL;
  22. using namespace std;
  23. const int N = 101010;
  24. int next_a[N],extand_a[N],next_c[N],extand_c[N];
  25. void getnext(char *T,int *next,int *extand) // next[i]: 以第i位置開始的子串 与 T的公共前缀
  26. {
  27. int i,length = strlen(T);
  28. next[0] = length;
  29. for(i = 0; i<length-1 && T[i]==T[i+1]; i++);
  30. next[1] = i;
  31. int a = 1;
  32. for(int k = 2; k < length; k++)
  33. {
  34. int p = a+next[a]-1, L = next[k-a];
  35. if( (k-1)+L >= p )
  36. {
  37. int j = (p-k+1)>0?
  38.  
  39. (p-k+1) : 0;
  40. while(k+j<length && T[k+j]==T[j]) j++;// 枚举(p+1,length) 与(p-k+1,length) 区间比較
  41. next[k] = j, a = k;
  42. }
  43. else next[k] = L;
  44. }
  45. }
  46. void getextand(char *S,char *T,int *next,int *extand) //s是母串,t是模式串
  47. {
  48. memset(next,0,sizeof(next));
  49. getnext(T,next,extand);
  50. int Slen = strlen(S), Tlen = strlen(T), a = 0;
  51. int MinLen = Slen>Tlen?
  52.  
  53. Tlen:Slen;
  54. while(a<MinLen && S[a]==T[a]) a++;
  55. extand[0] = a, a = 0;
  56. for(int k = 1; k < Slen; k++)
  57. {
  58. int p = a+extand[a]-1, L = next[k-a];
  59. if( (k-1)+L >= p )
  60. {
  61. int j = (p-k+1)>0? (p-k+1) : 0;
  62. while(k+j<Slen && j<Tlen && S[k+j]==T[j] ) j++;
  63. extand[k] = j;
  64. a = k;
  65. }
  66. else extand[k] = L;
  67. }
  68. }
  69. char a[100005],b[100005],c[100005],d[100005];
  70. LL t_a[100005],t_c[100005];
  71. void init()
  72. {
  73. memset(t_a,0,sizeof(t_a));
  74. memset(t_c,0,sizeof(t_c));
  75. }
  76. int main()
  77. {
  78. //freopen("1.txt","r",stdin);
  79. int T;
  80. scanf("%d",&T);
  81. while(T--)
  82. {
  83. init();
  84. scanf("%s",a);
  85. scanf("%s",b);
  86. int len_a=strlen(a);
  87. for(int i=0;i<len_a;i++)
  88. c[i]=a[len_a-1-i];
  89. c[len_a]='\0';
  90. int len_b=strlen(b);
  91. for(int i=0;i<len_b;i++)
  92. d[i]=b[len_b-1-i];
  93. d[len_b]='\0';
  94. getextand(a,b,next_a,extand_a);
  95. getextand(c,d,next_c,extand_c);
  96. for(int i=0;i<len_a;i++)
  97. {
  98. t_a[extand_a[i]]++;
  99. t_c[extand_c[i]]++;
  100. }
  101. for(int i=len_a-1;i>=1;i--)
  102. {
  103. t_a[i]+=t_a[i+1];
  104. t_c[i]+=t_c[i+1];
  105. }
  106. LL ans=0;
  107. for(int i=1;i<len_b;i++)
  108. {
  109. ans+=t_a[i]*t_c[len_b-i];
  110. }
  111. printf("%lld\n",ans);
  112. }
  113. return 0;
  114. }

ZOJ 3587 Marlon&#39;s String 扩展KMP的更多相关文章

  1. ZOJ 题目3587 Marlon&#39;s String(KMP)

    Marlon's String Time Limit: 2 Seconds      Memory Limit: 65536 KB Long long ago, there was a coder n ...

  2. acdream1116 Gao the string!(扩展KMP)

    今天是字符串填坑的一天,首先填的第一个坑是扩展KMP.总结一下KMP和扩展KMP的区别. 在这里s是主串,t是模式串. KMP可以求出的是以s[i]为结尾的串和 t前缀匹配的最长的长度.假如这个长度是 ...

  3. hdu3336 Count the string 扩展KMP

    It is well known that AekdyCoin is good at string problems as well as number theory problems. When g ...

  4. HDU-3336-Count the string(扩展KMP)

    链接: https://vjudge.net/problem/HDU-3336 题意: It is well known that AekdyCoin is good at string proble ...

  5. [2019杭电多校第五场][hdu6629]string matching(扩展kmp)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6629 题意求字符串的每个后缀与原串的最长公共前缀之和. 比赛时搞东搞西的,还搞了个后缀数组...队友一 ...

  6. 【string】KMP, 扩展KMP,trie,SA,ACAM,SAM,最小表示法

    [KMP] 学习KMP,我们先要知道KMP是干什么的. KMP?KMPLAYER?看**? 正如AC自动机,KMP为什么要叫KMP是因为它是由三个人共同研究得到的- .- 啊跑题了. KMP就是给出一 ...

  7. KMP && Manacher && 扩展KMP整理

    KMP算法: kmp示例代码: void cal_next(char *str, int *next, int len) { next[0] = -1;//next[0]初始化为-1,-1表示不存在相 ...

  8. 扩展KMP --- HDU 3613 Best Reward

    Best Reward Problem's Link:   http://acm.hdu.edu.cn/showproblem.php?pid=3613 Mean: 给你一个字符串,每个字符都有一个权 ...

  9. UVA5876 Writings on the Wall 扩展KMP

    扩展KMP的简单题. #include<stdio.h> #include<string.h> #define maxn 51010 char s[maxn],t[maxn]; ...

随机推荐

  1. [洛谷P1119][codevs1817]灾后重建

    题目大意:有n个村庄和一些连通两个村庄的双向道路.每个村庄在一个特定的时间修复.没有修复的村庄不能经过.现在有一系列询问,问两个村庄在t时刻的最短路(如果无法到达或两个村庄本身未修复,输出-1). 解 ...

  2. WPF获得PNG图片外观Path数据

    原文:WPF获得PNG图片外观Path数据        WPF开发界面的时候,用的最多的就是自定义控件模板,开发人员需要根据UI的设计,做出符合要求的自定义控件.但是在一些特殊情况下,UI的设计可能 ...

  3. struts2.x + Tiles2.x读取多个xml 配置文件

    在web.xml中配置如下即可: <context-param> <param-name>org.apache.tiles.impl.BasicTilesContainer.D ...

  4. silverlight wcf mvvm

    近期工作比較忙.也没有时间发表新内容,今天有点时间,就顺便写点,说说近期开发的一套系统心得. 我刚去这个公司已经将前端确定要用Silverlight,我不知道为什么要选择这个,或许是为以后转C/S系统 ...

  5. WEB前端,混合排版,有的宽有的窄,滚动会出现空白处,怎么办。

    多数时候出现空白都是由于有滚动栏滚到一边就会产生空白. overflow-x: hidden; 在最大图的那个div里写这句.

  6. Looger级别

    Logger级别 日志记录器(Logger)是日志处理的核心组件.log4j具有5种正常级别(Level).日志记录器(Logger)的可用级别Level (不包括自定义级别 Level), 以下内容 ...

  7. 理解ThreadLocal类

    1 ThreadLocal是什么 早在JDK 1.2的版本号中就提供java.lang.ThreadLocal,ThreadLocal为解决多线程程序的并发问题提供了一种新的思路. 使用这个工具类能够 ...

  8. springMVC --全局异常处理(两种方式)

    首先看springMVC的配置文件: <!-- 全局异常配置 start --> <bean id="exceptionResolver" class=" ...

  9. PHP 保留两位小数,且不四舍五入

    $value = '555.09988'; floor($value*100)/100;

  10. poj--1459--Power Network(最大流,超级源超级汇)

    Power Network Time Limit: 2000MS   Memory Limit: 32768KB   64bit IO Format: %I64d & %I64u Submit ...