您的位置:首页 > 其它

KMP字符串匹配算法

2016-07-06 22:41 232 查看
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace kmp
{
class Program
{
static void Main(string[] args)
{
string zstr, mstr;
zstr = Console.ReadLine();
mstr = Console.ReadLine();
int pos1;
pos1 = KMP(zstr, mstr);
if (pos1 == -1)
{
Console.WriteLine("没有匹配的字符串!");
}
else Console.WriteLine(pos1);
Console.Write("请按任意键继续。。");
Console.ReadKey(true);
}

//获取部分匹配表,函数求出模式串向右滑动位数
/*GetNextVal函数接受模式字符串str,假设str为ABCABD
* while循环是i小于5
* 第一次循环j=-1,next[1]=0
* 第二次循环i=1,j=0,str[1] str[0]不相同,执行else,j = next[j],j=-1
* 第三次循环i=1,j=-1, i++; j++; i=2,j=0;next[2]=0
* 第四次循环i=2,j=0,执行else,j=next[0] = -1
* 第五次循环i=2,j=-1,i++; j++; i=3,j=0;next[3]=0
* 第六次循环i=3,j=0,str[3] == str[0],i++; j++;next[4] = 1
* 第七次循环i=4,j=1,str[4] == str[1],i++; j++; next[5] = 2
* 第八次while不满足,next[] = {-1,0,0,0,1,2}
*/
static void GetNextVal(string str, int[] next)
{
int i = 0;
int j = -1;
next[0] = -1;
while (i < str.Length - 1)
{
if (j == -1 || str[i] == str[j])
{
i++; j++;
next[i] = j;
}
else
{
j = next[j];
}
}

}

/*在字符串zstr中寻找匹配mstr*/
static int KMP(string zstr, string mstr)
{
int i, j;
//假设mstr为ABCABD,则next[]长度为6
int[] next = new int[mstr.Length];
//GetNextVal得到next[] = {-1,0,0,0,1,2}
GetNextVal(mstr, next);
i = 0; j = 0;
/*假设zstr输入了ASABCABDAS
* 匹配         ABCABD
* WHILE i<10,j<6
* 第一次循环zstr[0] = mstr[0],i=1,j=1
* 第二次循环,else j=0
* 第三次循环时i=1 ,j=0 else j=-1
* 第四次循环i=2,j=0
* 第五次循环zstr[2] == mstr[0],i=3,j=1
* 第六次循环zstr[3] == mstr[1]
*               .
*               .
*               .
* 第十次循环zstr[7] == mstr[5], i=8,j=6,while循环结束
*/
while (i < zstr.Length && j < mstr.Length)
{
if (j == -1 || zstr[i] == mstr[j])
{
++i; ++j;
}
else
{
j = next[j];
}
}
if (j == mstr.Length)
//return 8 - 6 = 2
return i - mstr.Length;
//否则的话,没有找到匹配字符串,返回-1
return -1;
}
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: