《kmp算法》

61 阅读1分钟
#include <bits/stdc++.h>

using i64 = long long;

const int N = 100010, M = 1000010;

int n, m;
char P[N], S[M];// 模板串(短)与模式串(长)
int next[N];// 前缀与后缀的最长共有元素的长度,kmp算法的核心

int main() {
	std::ios::sync_with_stdio(false);
	std::cin.tie(nullptr);

	// 读入
	std::cin >> n >> P + 1 >> m >> S + 1;

	// 求next数组的过程
	for (int i = 2, j = 0; i <= n; i ++) {
		while (j && P[i] != P[j + 1]) {
			j = next[j];
		}
		j += (P[i] == P[j + 1]);
		next[i] = j;
	}

	// kmp匹配过程
	for (int i = 1, j = 0; i <= m; i ++) {
		while (j && S[i] != P[j + 1]) {
			j = next[j];
		}
		j += (S[i] == P[j + 1]);
		if (j == n) {
			std::cout << i - n << " ";
			j = next[j];
		}
	}

	return 0;
}
// AcWing 831. KMP字符串