implement kmp algorithm, all tests passed.

This commit is contained in:
Shine wOng
2019-08-21 20:57:29 +08:00
parent c543b8173f
commit a97fdd2895
4 changed files with 79 additions and 0 deletions

28
thu_dsa/chp11/kmp.cpp Normal file
View File

@@ -0,0 +1,28 @@
#include "kmp.h"
#include <iostream>
int* makeNext(char* str){
int* next;
int len, i = 0, j = -1;
for (len = 0; str[len] != '\0'; ++len);
next = new int[len];
next[0] = -1;
while(i < len - 1){
if(j < 0 || str[i] == str[j]) next[++i] = ++j;
else j = next[j];
}
return next;
}
int match(char* text, char* pattern){
int* next = makeNext(pattern);
int i = 0, j = 0, m = strlen(text), n = strlen(pattern);
while(i < m && j < n){
if(j < 0 || text[i] == pattern[j]){
++i;
++j;
}
else j = next[j];
}
return i - j;
}

7
thu_dsa/chp11/kmp.h Normal file
View File

@@ -0,0 +1,7 @@
#ifndef KMP_H_
#define KMP_H_
int* makeNext(char* str);
int match(char* text, char* pattern);
#endif

9
thu_dsa/chp11/string.md Normal file
View File

@@ -0,0 +1,9 @@
Conclusions on String
====================
+ `串`的特点:串长要远远大于字母表的大小
## KMP
> 为什么要取最长自匹配?
快速右移 + 避免回退。(怎么理解)

View File

@@ -0,0 +1,35 @@
#include "kmp.h"
#include <iostream>
#include <cassert>
using std::cout;
using std::endl;
void test_make_next(){
char* str = "chine chinchilla";
int exp[] = { -1, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 1, 2, 3, 0, 0 };
int* result = makeNext(str);
for (int ix = 0; ix != strlen(str); ++ix)
assert(exp[ix] == result[ix]);
}
void test_match(){
char* text = "chine chinchilla";
char* p1 = "chine";
char* p2 = "chinc";
char* p3 = "chinec";
assert(match(text, p1) == 0);
assert(match(text, p2) == 6);
assert(match(text, p3) == 16);
}
int main(){
cout << "begin tests..." << endl;
test_make_next();
test_match();
cout << "All tests passed." << endl;
system("pause");
return 0;
}