簡易KMP

給定一個模式串S,以及一個模板串P,所有字符串中只包含大小寫英文字母以及阿拉伯數字。 模板串P在模式串S中多次作爲子串出現。 求出模板串P在模式串S中所有出現的位置的起始下標。

輸入格式

第一行輸入整數N,表示字符串P的長度。

第二行輸入字符串P。

第三行輸入整數M,表示字符串S的長度。

第四行輸入字符串S。

輸出格式

共一行,輸出所有出現位置的起始下標(下標從0開始計數),整數之間用空格隔開。

數據範圍

1≤N≤104

1≤M≤105

輸入樣例:

3
aba
5
ababa

輸出樣例:

0 2

#include <iostream>
using namespace std;
const int N = 10010, M = 100010;

int n, m;//模式串和子串的長度
char p[N], s[M];//p是模板串, s是模式串
int ne[N];//next數組,取當前字符最大前綴後綴相等的個數,也就是最長公共前綴
int main()
{
	cin >> n >> p + 1 >> m >> s + 1;//輸入長度及串內容
	
	//求next的過程
	ne[1] = 0;//下標從1開始
	for(int i = 2, j = 0; i <= n; i ++ )
	{
		while(j && p[i] != p[j + 1])
			j = ne[j];
		if(p[i] == p[j + 1]) j ++ ;
		ne[i] = j;
	 } 
	
	//KMP匹配過程
	for(int i = 1, j = 0; i <= m; i ++ )
	{
		while(j && s[i] != p[j + 1]) 
			j = ne[j];
		if(s[i] == p[j + 1]) 
			j ++ ;
		if(j == n)
		{
			//匹配成功
			printf("%d ", i - n );
			j = ne[j]; 
		}
	 } 
	 return 0;
}

理解 + 記憶

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章