一、题目描述
长为n的字符串中匹配长度为m的子串
二、 算法分析
1、简单匹配:将主串S中某个位置i起始的子串和模式串T相比较。即从
2、KMP算法
1)、求串的模式值
(1)next[0]= -1 意义:任何串的第一个字符的模式值规定为-1。
(2)next[j]= -1 意义:模式串T中下标为j的字符,如果与首字符相同,且j的前面的1—k个字符与开头的1—k个字符不等(或者相等但T[k]==T[j])(1≤k<j)。如:T=”abCabCad” 则 next[6]=-1,因T[3]=T[6]
(3)next[j]=k 意义:模式串T中下标为j的字符,如果j的前面k个字符与开头的k个字符相等,且T[j] != T[k](1≤k<j)。即T[0]T[1]T[2]。。。T[k-1]==T[j-k]T[j-k+1]T[j-k+2]…T[j-1]且T[j] != T[k].(1≤k<j);
(4) next[j]=0 意义:除(1)(2)(3)的其他情况。
void get_nextval(const cha<pre name="code" class="cpp">void get_nextval(const char *Tvoid getInterval( const char*T,int next[])
{
// 求模式串T的next函数值并存入数组 next。
int j = 0, k = -1;
next[0] = -1;
while ( T[j] != '/0' )
{
if (k == -1 || T[j] == T[k])
{
++j; ++k;
if (T[j]!=T[k])
next[j] = k;
else
next[j] = next[k];
}
else
k = next[k];
}
}
2)
int KMP(const char *Text,con int KMP(const char*Text,const char* Pattern) //const 表示函数内部不会改变这个参数的值。
{
if( !Text||!Pattern|| Pattern[0]=='\0' || Text[0]=='\0' )//
return -1;//空指针或空串,返回-1。
int len=0;
const char *c=Pattern;
while(*c++!='\0')//移动指针比移动下标快。
++len;//字符串长度。
int *next=new int[len+1];
get_nextval(Pattern,next);//求Pattern的next函数值
int index=0,i=0,j=0;
while(Text[i]!='\0' && Pattern[j]!='\0' ){
if(Text[i]== Pattern[j]){
++i;// 继续比较后继字符
++j;
}
else{
index += j-next[j];
if(next[j]!=-1)
j=next[j];// 模式串向右移动
else{
j=0;
++i;
}
}
}//while
delete []next;
if(Pattern[j]=='\0')
return index;// 匹配成功,返回匹配首字符下标
else
return -1;
}
3、复杂度
o(m)+o(n)
int