用扩展KMP做简单省力.....

D. Prefixes and Suffixes
time limit per test

1 second

memory limit per test

256 megabytes

input

standard input

output

standard output

You have a string s = s1s2...s|s|,
where |s| is the length of string s, and si its i-th
character.

Let's introduce several definitions:

  • A substring s[i..j] (1 ≤ i ≤ j ≤ |s|) of
    string s is string sisi + 1...sj.
  • The prefix of string s of length l (1 ≤ l ≤ |s|) is
    string s[1..l].
  • The suffix of string s of length l (1 ≤ l ≤ |s|) is
    string s[|s| - l + 1..|s|].

Your task is, for any prefix of string s which matches a suffix of string s,
print the number of times it occurs in string s as a substring.

Input

The single line contains a sequence of characters s1s2...s|s| (1 ≤ |s| ≤ 105) —
string s. The string only consists of uppercase English letters.

Output

In the first line, print integer k (0 ≤ k ≤ |s|) —
the number of prefixes that match a suffix of string s. Next print k lines,
in each line print two integers li ci.
Numbers li ci mean
that the prefix of the length li matches
the suffix of length li and
occurs in string s as a substringci times.
Print pairs li ci in
the order of increasing li.

Sample test(s)
input
ABACABA
output
3
1 4
3 2
7 1
input
AAA
output
3
1 3
2 2
3 1

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm> using namespace std; const int maxn=100100; char T[maxn],P[maxn];
int next[maxn],ex[maxn]; void pre_exkmp(char P[])
{
int m=strlen(P);
next[0]=m;
int j=0,k=1;
while(j+1<m&&P[j]==P[j+1]) j++;
next[1]=j;
for(int i=2;i<m;i++)
{
int p=next[k]+k-1;
int L=next[i-k];
if(i+L<p+1) next[i]=L;
else
{
j=max(0,p-i+1);
while(i+j<m&&P[i+j]==P[j]) j++;
next[i]=j; k=i;
}
}
} void exkmp(char P[],char T[])
{
int m=strlen(P),n=strlen(T);
pre_exkmp(P);
int j=0,k=0;
while(j<n&&j<m&&P[j]==T[j]) j++;
ex[0]=j;
for(int i=1;i<n;i++)
{
int p=ex[k]+k-1;
int L=next[i-k];
if(i+L<p+1) ex[i]=L;
else
{
j=max(0,p-i+1);
while(i+j<n&&j<m&&T[i+j]==P[j]) j++;
ex[i]=j; k=i;
}
}
} int pos[maxn],sum[maxn],mx=-1; struct ANS
{
int a,b;
}ans[maxn];
int na=0; bool cmp(ANS x,ANS y)
{
if(x.a!=y.a)return x.a<y.a;
return x.b<y.b;
} int lisan[maxn],nl; int main()
{
cin>>P;
pre_exkmp(P);
int n=strlen(P);
for(int i=0;i<n;i++)
{
pos[next[i]]++;
lisan[nl++]=next[i];
mx=max(mx,next[i]);
}
sort(lisan,lisan+nl);
int t=unique(lisan,lisan+nl)-lisan;
for(int i=t-1;i>=0;i--)
{
sum[lisan[i]]=sum[lisan[i+1]]+pos[lisan[i]];
}
for(int i=0;i<n;i++)
{
if(next[i]==n-i)
{
ans[na++]=(ANS){next[i],sum[next[i]]};
}
}
sort(ans,ans+na,cmp);
printf("%d\n",na);
for(int i=0;i<na;i++)
{
printf("%d %d\n",ans[i].a,ans[i].b);
}
return 0;
}

Codeforces 432 D. Prefixes and Suffixes的更多相关文章

  1. Codeforces 432D Prefixes and Suffixes kmp

    手动转田神的大作:http://blog.csdn.net/tc_to_top/article/details/38793973 D. Prefixes and Suffixes time limit ...

  2. Codeforces 432D Prefixes and Suffixes(KMP+dp)

    题目连接:Codeforces 432D Prefixes and Suffixes 题目大意:给出一个字符串,求全部既是前缀串又是后缀串的字符串出现了几次. 解题思路:依据性质能够依据KMP算法求出 ...

  3. CodeForces Round #527 (Div3) C. Prefixes and Suffixes

    http://codeforces.com/contest/1092/problem/C Ivan wants to play a game with you. He picked some stri ...

  4. Codeforces Round #246 (Div. 2) D. Prefixes and Suffixes

                                                        D. Prefixes and Suffixes You have a string s = s ...

  5. Codeforces Round #246 (Div. 2) D. Prefixes and Suffixes(后缀数组orKMP)

    D. Prefixes and Suffixes time limit per test 1 second memory limit per test 256 megabytes input stan ...

  6. Codeforces 1092C Prefixes and Suffixes(思维)

    题目链接:Prefixes and Suffixes 题意:给定未知字符串长度n,给出2n-2个字符串,其中n-1个为未知字符串的前缀(n-1个字符串长度从1到n-1),另外n-1个为未知字符串的后缀 ...

  7. codeforces432D Prefixes and Suffixes(kmp+dp)

    转载请注明出处: http://www.cnblogs.com/fraud/          ——by fraud D. Prefixes and Suffixes You have a strin ...

  8. CF432D Prefixes and Suffixes

    CF432D Prefixes and Suffixes 题意 给你一个长度为n的长字符串,"完美子串"既是它的前缀也是它的后缀,求"完美子串"的个数且统计这些 ...

  9. codeforces - 432D Prefixes and Suffixes (next数组)

    http://codeforces.com/problemset/problem/432/D 转自:https://blog.csdn.net/tc_to_top/article/details/38 ...

随机推荐

  1. MySQL如何修改root密码

    MySQL修改用户密码         因为长期不登录MySQL数据库,登录时经常忘记root权限密码.本文提供一个在数据库服务器上修改root密码的方法,本文撰写基础是在xp操作系统下进行. 第一步 ...

  2. HDU 1142 A Walk Through the Forest(dijkstra+记忆化DFS)

    题意: 给你一个图,找最短路.但是有个非一般的的条件:如果a,b之间有路,且你选择要走这条路,那么必须保证a到终点的所有路都小于b到终点的一条路.问满足这样的路径条数 有多少,噶呜~~题意是搜了解题报 ...

  3. delphi 使用superobject实现jsonrpc的http远程调用 good

    http://blog.csdn.net/earbao/article/details/46423167

  4. java学习笔记12--国际化

    java学习笔记12--国际化 国际化的操作就是指一个程序可以同时适应多门语言,即:如果现在程序者是中国人,则会以中文为显示文字,如果现在程序的使用者是英国人,则会以英语为显示的文字,也就是说可以通过 ...

  5. MySql 链接url 参数详解

    最近 整理了一下网上关于MySql 链接url 参数的设置,有不正确的地方希望大家多多指教: mysql JDBC URL格式如下: jdbc:mysql://[host:port],[host:po ...

  6. 小猪的Android入门之路 day 1

    小猪的Android入门之路 Day 1 Android相关背景与开发环境的搭建 ------转载请注明出处:coder-pig 本节引言: 随着社会经济的发展,移动互联网的越来越热,手机APP开发显 ...

  7. poj 3270 更换使用

    1.确定初始和目标状态. 明确.目标状态的排序状态. 2.得出置换群,.比如,数字是8 4 5 3 2 7,目标状态是2 3 4 5 7 8.能写为两个循环:(8 2 7)(4 3 5). 3.观察当 ...

  8. WOJ 1055

    #include<stdio.h> #include<stdlib.h> #include<string.h> int main() { char s[6]={0} ...

  9. poj3678(two-sat)

    传送门:Katu Puzzl 题意:n个点,点的取值可以是0或者1.m条边,有权值,有运算方式(并,或,异或),要求和这条边相连的两个点经过边上的运算后的结果是边的权值.问你有没有可能把每个点赋值满足 ...

  10. Matlab---串口操作---数据採集篇

    matlab功能强大,串口操作也非常easy.相信看过下面两个实验你就能掌握咯! 開始吧! 实验1: 从电脑COM2口读取数据.并将数据保存在TXT文件里,方便数据分析,以下是M脚本: %名 称:Ma ...