给两个字符串,问前者在后者中出现了多少次,出现次数可以覆盖
*解法:kmp,理解好next数组的含义,第一次匹配完成后,i不变,j = next[j]即可
#include <iostream> #include <cstdio> #include <cstring> using namespace std; #define SZ 10005 #define MAXN 1000005 #define INF 1e9+10 int nxt[SZ]; char s[MAXN], p[SZ]; int slen, plen;//每次都调用strlen会浪费时间 void get_next(char p[]) { int i = 0, j = -1; nxt[0] = -1; while(i < plen - 1) { if(j == -1 || p[i] == p[j]) { i++; j++; nxt[i] = j; } else j = nxt[j]; } return; } int kmp(char p[], char s[]) { int i = 0, j = 0, cnt = 0; while(i < slen && j < plen) { if(j == -1 || s[i] == p[j]) { i++; j++; } else j = nxt[j]; if(j == plen) { cnt++; j = nxt[j]; } } return cnt; } int main() { int T; scanf("%d", &T); while(T--) { scanf(" %s %s", p, s); plen = strlen(p); slen = strlen(s); get_next(p); int cnt = kmp(p, s); printf("%d\n", cnt); } return 0; }