kmp(前缀出现次数next应用)

http://acm.hdu.edu.cn/showproblem.php?pid=3336

Count the string

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 17068    Accepted Submission(s): 7721

Problem Description

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

Author

[email protected]

Source

HDOJ Monthly Contest – 2010.03.06

Recommend

lcy

题意:求字符串所有前缀出现的次数(包括本身)

思路:求所有next的值的个数加上前缀本身

#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <iostream>
#include <algorithm>
#include <iostream>
#include<cstdio>
#include<string>
#include<cstring>
#include <stdio.h>
#include <string.h>
using namespace std;
char a[200009];

int num;

void getnext(char* a, int len , int *next)
{
    next[0] = -1 ;
    int k = -1 , j = 0 ;
    while(j < len)
    {
        if(k == -1 || a[j] == a[k])
        {
            k++;
            j++;
        //    if(a[j] != a[k])
                next[j] = k ;
          //  else
          //  {
          //      next[j] = next[k];
           // }

        }
        else
        {
            k = next[k];
        }
    }
}

int main()
{int n ;
    scanf("%d" , &n);
    while(n--)
    {
        int next[200009];
        int l ;
        scanf("%d" , &l);
        scanf("%s" , a);
        getnext(a , l , next);
        int j = 0 ;
        for(int i = 0 ; i <= l ; i++)
        {
        //    cout << next[i] << " " ;
            j = i ;
            while(next[j] > 0)
            {
                num = (num + 1) % 10007 ;
                j = next[j];
            }
        }
       // cout << endl ;

        printf("%d\n" , (num + l)%10007);
        num = 0 ;
    }

    return 0 ;
}

原文地址:https://www.cnblogs.com/nonames/p/11296242.html

时间: 2025-01-14 21:50:15

kmp(前缀出现次数next应用)的相关文章

51nod 1277 KMP 前缀出现次数

51NOD 1277:http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1277 跟HDU 6153还挺像的:http://www.cnblogs.com/Egoist-/p/7435573.html 相比与上面那个题,这个还要相对简单一些,只需要处理模式串自己就好了. 一开始写麻烦了,直接套了HDU6153的代码,后来发现--他就是个模式串本身的匹配,我干嘛弄那么麻烦Orz 题意:找前缀长度*出现次数的最大值,长度好说,

HDOJ3336 Count the string 【KMP前缀数组】+【动态规划】

Count the string Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 4212    Accepted Submission(s): 1962 Problem Description It is well known that AekdyCoin is good at string problems as well as n

HDU 3336 Count the string (KMP next数组运用——统计前缀出现次数)

Count the string Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 6375    Accepted Submission(s): 2947 Problem Description It is well known that AekdyCoin is good at string problems as well as nu

HDU4300-Clairewd’s message(KMP前缀匹配后缀)

Clairewd's message Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 3228    Accepted Submission(s): 1248 Problem Description Clairewd is a member of FBI. After several years concealing in BUPT,

HDU4763-Theme Section(KMP+二分)

Theme Section Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 1098    Accepted Submission(s): 570 Problem Description It's time for music! A lot of popular musicians are invited to join us in t

hdu3336解读KMP算法的next数组

查看原题 题意大致是:给你一个字符串算这里面所有前缀出现的次数和.比如字符串abab,a出现2次,ab出现2次,aba出现1次,abab出现1次.总计6次. 并且结果太大,要求对1007进行模运算. AC代码 #include <iostream> using namespace std; #include <string> string s; int n,Next[200005]; void getNext() { int len = n; Next[0]=-1; int i=0

[hdu3336]kmp(后缀数组)

题意:求字符串s的所有前缀出现次数之和. http://www.cnblogs.com/jklongint/p/4446117.html 思路:用kmp做,简单且效率高.以前缀结尾的位置分类,令dp[i]为以结尾位置在i的前缀数量,那么dp[i] = cnt(j)(j~i是前缀),而由kmp的next函数的转移性质,可得如下递推方程:dp[i] = dp[next[i]] + 1,把这个递推式不断展开,也就是i = next[i]不断迭代,那么+1的个数就是dp[i] = cnt(j)(j~i是

HDU Count the string (KMP)

题面见http://acm.hdu.edu.cn/showproblem.php?pid=3336 给你一个字符串,让你找它的前缀在整个字符串出现的次数. 作为一个不会思考的笨比,直接用kmp去一个个计数,果不其然,t了 找了博客来看,大概就是kmp+dp,要用到kmp中的pret数组(有的人习惯叫next数组,知道就行) dp的方程形式很简单,但很难理解. 这是原博主的原话: 如果用dp[i]表示该字符串前i个字符中出现任意以第i个字符结尾的前缀的次数,它的递推式是 dp[i]=dp[pret

ZOJ 3587 扩展KMP

思路:这题确实大帝做得很机智!字符串先求最长前缀,反的字符串再求一次最长前缀,然后就可以搞了. 每个子串出现的次数就是最长前缀的次数嘛! #pragma comment(linker, "/STACK:1024000000,1024000000") #include<iostream> #include<cstdio> #include<cstring> #include<algorithm> #include<map> #i