Problem-solving ideas
——Because an array has been reduced and adjusted for 1 hour, I am speechless...TOT
Because the data is not big for this question, you can run n 2 n^2 directlyn2 .
Consider enumerating the left end point, let the left end point bel, S = C [l, ∣ C ∣] l, S=C[l,|C|]l,S=C[l,∣ C ∣ ] , then runKMP KMPon the string SK M P .
Then in the statistical process, assuming that it is now at position i, thenS [1, j] = S [i − j + 1, i] S[1,j]=S[i-j+1,i]S[1,j]=S[i−j+1,i]。如果 j ∗ 2 > = i j*2>=i j∗2>=i , then let j=p[j], at this timeA [1, j] = a [i − j + 1, i], j A[1,j]=a[i-j+1,i], jA[1,j]=a[i−j+1,i ] , j keeps jumping back along the pointer untilj ∗ 2 <ij*2<ij∗2<i . Then judge whether j is greater than or equal to k, and if so, add up the answers.
Code
#include<iostream>
#include<cstdio>
#include<iomanip>
#include<cstring>
#include<algorithm>
#include<cmath>
using namespace std;
char s[20010],c[20010];
int ans,j,k,l,len,m,p[20010];
int main() {
scanf("%s",c+1);
scanf("%d",&k);
len=strlen(c+1);
for(register int t=1; t<=len; t++) {
memset(s,0,sizeof(s));
memset(p,0,sizeof(p));
for(register int w=1;w+t-1<=len;w++)
s[w]=c[w+t-1]; //处理左端点
j=0,l=strlen(s+1);
for(register int i=2; i<=l; i++) {
while(j&&s[i]!=s[j+1])
j=p[j];
if(s[i]==s[j+1])
j++;
p[i]=j;
}
j=0;
for(register int i=1; i<=l; i++) {
while(j&&s[i]!=s[j+1])
j=p[j];
if(s[i]==s[j+1])
j++;
while((j<<1)>=i)j=p[j];
if(j>=k)ans++;
}
}
printf("%d",ans);
}