It is well known that AekdyCoin is good at string problems as well as number theory problems. When given a string s, we can write down all the non-empty prefixes of this string. For example: 
  s: "abab" 
  The prefixes are: "a", "ab", "aba", "abab" 
  For each prefix, we can count the times it matches in s. So we can see that prefix "a" matches twice, "ab" matches twice too, "aba" matches once, and "abab" matches once. Now you are asked to calculate the sum of the match times for all the prefixes. For "abab", it is 2 + 2 + 1 + 1 = 6. The answer may be very large, so output the answer mod 10007. 
Input
  The first line is a single integer T, indicating the number of test cases. 

  For each case, the first line is an integer n (1 <= n <= 200000), which is the length of string s. A line follows giving the string s. The characters in the strings are all lower-case letters. 
Output

  For each case, output only one number: the sum of the match times for all the prefixes of s mod 10007.

Sample Input

1
4
abab

Sample Output

6

  可以确定肯定不能拿每个前缀跑去KMP,那么来回想一下fail(next)数组的意义——最长相同的前缀和后缀。对于长度为i的前缀,那么f[i]中包含两个长度为f[i]的前缀(大概就这个意思),用cnt[i]表示1-i这一段中有多少个子串与长度为f[i],f[f[i]]的前缀相同(除去cnt[f[i]]这一部分),于是可以得出

  cnt[i] = cnt[f[i]] + 1

  最后把所有cnt求个和就是最终答案

Code

 /**
* hdu
* Problem#3336
* Accepted
* Time:46ms
* Memory:3316k
*/
#include<iostream>
#include<cstdio>
#include<cctype>
#include<cstring>
#include<cstdlib>
#include<fstream>
#include<sstream>
#include<algorithm>
#include<map>
#include<ctime>
#include<set>
#include<queue>
#include<vector>
#include<stack>
using namespace std;
typedef bool boolean;
#define INF 0xfffffff
#define smin(a, b) a = min(a, b)
#define smax(a, b) a = max(a, b)
#ifndef WIN32
#define AUTO "%lld"
#else
#define AUTO "%I64d"
#endif
template<typename T>
inline void readInteger(T& u){
char x;
int aFlag = ;
while(!isdigit((x = getchar())) && x != '-');
if(x == '-'){
x = getchar();
aFlag = -;
}
for(u = x - ''; isdigit((x = getchar())); u = (u << ) + (u << ) + x - '');
ungetc(x, stdin);
u *= aFlag;
} int kase;
int n;
char s[];
int f[];
int cnt[]; inline void init() {
readInteger(n);
gets(s);
gets(s);
} inline void solve() {
f[] = f[] = ;
int j;
for(int i = ; i < n; i++) {
j = f[i];
while(j > && s[i] != s[j]) j = f[j];
f[i + ] = (s[i] == s[j]) ? (j + ) : ();
}
int res = ;
for(int i = ; i <= n; i++)
(cnt[i] = cnt[f[i]] + ) %= , (res += cnt[i]) %= ;
printf("%d\n", res);
} int main() {
readInteger(kase);
while(kase--) {
init();
solve();
}
return ;
}

hdu 3336 Count the string -KMP&dp的更多相关文章

  1. hdu 3336 Count the string KMP+DP优化

    Count the string Problem Description It is well known that AekdyCoin is good at string problems as w ...

  2. [HDU 3336]Count the String[kmp][DP]

    题意: 求一个字符串的所有前缀串的匹配次数之和. 思路: 首先仔细思考: 前缀串匹配. n个位置, 以每一个位置为结尾, 就可以得到对应的一个前缀串. 对于一个前缀串, 我们需要计算它的匹配次数. k ...

  3. HDU 3336 Count the string ( KMP next函数的应用 + DP )

    dp[i]代表前i个字符组成的串中所有前缀出现的次数. dp[i] = dp[next[i]] + 1; 因为next函数的含义是str[1]~str[ next[i] ]等于str[ len-nex ...

  4. HDU 3336 Count the string KMP

    题目地址:http://acm.hdu.edu.cn/showproblem.php?pid=3336 如果你是ACMer,那么请点击看下 题意:求每一个的前缀在母串中出现次数的总和. AC代码: # ...

  5. HDU 3336 Count the string(KMP的Next数组应用+DP)

    Count the string Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) ...

  6. hdu 3336:Count the string(数据结构,串,KMP算法)

    Count the string Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) ...

  7. HDU 3336 Count the string(next数组运用)

    Count the string Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) ...

  8. HDU 3336 Count the string 查找匹配字符串

    Count the string Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) ...

  9. hdu 3336 count the string(KMP+dp)

    题意: 求给定字符串,包含的其前缀的数量. 分析: 就是求所有前缀在字符串出现的次数的和,可以用KMP的性质,以j结尾的串包含的串的数量,就是next[j]结尾串包含前缀的数量再加上自身是前缀,dp[ ...

随机推荐

  1. create view in view

    CREATE VIEW view_region2role AS ( SELECT region_set_id, region_set_name, GROUP_CONCAT(id) gc_id, GRO ...

  2. vs code 设置工作区背景图片方法

    1.扩展--安装background 2.文件--首选项--设置--在settings.josn中编辑--右侧用户设置添加 "background.useFront": false ...

  3. Spark-Cache与Checkpoint

    一.Cache缓存操作 scala> val rdd1 = sc.textFile("hdfs://192.168.146.111:9000/logs") rdd1: org ...

  4. kubernetes实战(二十五):kubeadm 安装 高可用 k8s v1.13.x

    1.系统环境 使用kubeadm安装高可用k8s v.13.x较为简单,相比以往的版本省去了很多步骤. kubeadm安装高可用k8s v.11 和 v1.12 点我 主机信息 主机名 IP地址 说明 ...

  5. 人活着系列之芳姐和芳姐的猪(Floyd)

    http://acm.sdut.edu.cn/sdutoj/problem.php?action=showproblem&problemid=2929 这个题一方面数据水,另一方面就是思维水, ...

  6. 什么是anaconda【转载】

    转自:https://zhidao.baidu.com/question/525102108723657245.html https://zhidao.baidu.com/question/62475 ...

  7. [LeetCode] 152. Maximum Product Subarray_Medium tag: Dynamic Programming

    Given an integer array nums, find the contiguous subarray within an array (containing at least one n ...

  8. TensorFlow 开发环境搭建--Pycharm

    今天动手开始搭建TensorFlow开发环境, 用PyCharm来跑MNIST中的例子.记录过程如下 下载安装 (1)首先安装AnaConda, AnaConda可以帮忙去管理安装包,帮忙创建虚拟环境 ...

  9. excel输入数字变成特殊符号问题

    问题,在单元格里输入数字,结果变成文件夹类型的小图片或特殊符号了,原因是字体为Wingdings,将其设为Times New Roman即可

  10. VS2010/MFC编程入门之三十九(文档、视图和框架:概述)

    前面几节讲了菜单.工具栏和状态栏的使用,鸡啄米本节开始将为大家讲解文档.视图和框架的知识. 文档.视图和框架简介 在VS2010/MFC编程入门之三十四(菜单:VS2010菜单资源详解)创建的单文档工 ...