KMP算法在字符串方面有着廣泛的應用,敏感詞過濾,分詞等。
使用C#實現了一把,作爲備忘。
i指針回溯的算法爲:
代碼
public int Index(string s, string t)
{
int i =0,j=0;
while (i < s.Length && j < t.Length)
{
if (j==0||s[i] == t[j])
{
i++;
j++;
}
else
{
i = i - j + 1;//i指針在此處回溯
j = 0;
}
}
if (j >= t.Length) return i - j;
else
return -1;
}
{
int i =0,j=0;
while (i < s.Length && j < t.Length)
{
if (j==0||s[i] == t[j])
{
i++;
j++;
}
else
{
i = i - j + 1;//i指針在此處回溯
j = 0;
}
}
if (j >= t.Length) return i - j;
else
return -1;
}
KMP算法就是字符串i指針不回溯,跟模式串指針j處的字符再比較。難點就是求Next值(構造失敗指針),即從已匹配的“部分匹配”中找出一個最大的子匹配模式串。
數學公式爲:S[0,k-1]== S[i- k, i-1]
KMP求Next
private int[] GetNext(string t)
{
int len = t.Length;
int[] next =new int[len];
int i = 1,j = 0;
while (i < len - 1)
{
if (j==0||t[i] == t[j])
{
i++;
j++;
next[i] = j;
}
else
j = next[j];
}
return next;
}
{
int len = t.Length;
int[] next =new int[len];
int i = 1,j = 0;
while (i < len - 1)
{
if (j==0||t[i] == t[j])
{
i++;
j++;
next[i] = j;
}
else
j = next[j];
}
return next;
}
KMP算法:
KMP
public int KmpIndex(string s, string t)
{
int i = 0, j = 0;
int[] next = GetNext(t);
while (i < s.Length && j < t.Length)
{
if (j==0||s[i] == t[j])
{
i++;
j++;
}
else
j=next[j];
}
if (j >= t.Length) return i - j;
else
return -1;
}
{
int i = 0, j = 0;
int[] next = GetNext(t);
while (i < s.Length && j < t.Length)
{
if (j==0||s[i] == t[j])
{
i++;
j++;
}
else
j=next[j];
}
if (j >= t.Length) return i - j;
else
return -1;
}