利用C++中的<string>类实现KMP算法

    KMP算法真的是“大牛”算法,我想了好几天才把它真正弄懂实现出来,真真不容易!啥都不说了,代码说明一切。

#include<iostream>
using namespace std;
#include<string>
int Brute_Force(string S, string T) 
{
	unsigned int i = 0;
	unsigned int j = 0;
	int pos = -1;  
	while (i < S.length()&&j < T.length()) { // 循环比较的条件
		if (S[i] == T[j]) {// 如果相等 则继续比较
			i++;
			j++;
		}
		else { // 不相等则让指向主串的“移动指针”i回溯,让指向模式串的“移动指针”j指向初始位置0
			i = i - (j - 1); // 主串的“移动指针”i应该回溯(i-1)个单位
			j = 0;
		}
	}
	// 如果j>=T.length() 则说明匹配成功  那么修改pos
	if (j >= T.length()) {
		pos = i - T.length();
		return pos;
	}
	else {// 否则直接-1
		return -1;
	}
}


// 获得next[]数组
void GetNext(string T, int next[])
{
	int j = 0;
	int k = -1;
	next[0] = -1;
	while (j < T.length()-1) {
		if (k == -1 || T[j] == T[k])
			next[++j] = ++k;	// 这里容易出错
		else
			k = next[k];
	}
	
}


// 获得nextVal数组
void GetNextVal(string T, int nextval[])
{
	int j = 0;
	int k = -1;
	nextval[0] = -1;
	while (j < T.length()-1 ) {
		if (k == -1 || T[j] == T[k]) {
			if (T[++j] == T[++k]) // 这句容易出错 
				nextval[j] = nextval[k];
			else
				nextval[j] = k;
		}
		else
			k = nextval[k];
	}
}



int KMP(string S, string T,int next[])
{
	int i = 0; // 主串的位置
	int j = 0; // 模式串的位置
	while (i < S.length() && j < T.length()) {
		if (S[i] == T[j]) {
			i++;
			j++;
		}
		else if (j == 0) i++; // 这句值钱
		else
			j = j - (j - next[j]); //模式串指针回溯(j-next[j])
	}
	if (j == T.length())
		return i - j;
	else
		return -1;
}


int main()
{
	string a = "aabdbababbbssdabacababcc";
	string b = "abacababcc";
	cout << Brute_Force(a, b) << endl;

	int* pnext = new int[b.length()];
	int* pnextVal = new int[b.length()];

	GetNext(b, pnext);
	for (int i = 0; i < b.length(); i++) {
		cout << pnext[i] << " ";
	}
	cout << endl;


	GetNextVal(b, pnextVal);
	for (int i = 0; i < b.length(); i++) {
		cout << pnextVal[i] << " ";
	}
	cout << endl;

	cout << KMP(a, b, pnext) << endl;
	
	delete[] pnext;
	delete[]pnextVal;
	return 0;
}

运行结果如下图:


猜你喜欢

转载自blog.csdn.net/CholenMine/article/details/80726954
今日推荐