学习目标:
1、概念
串匹配:在一个串(字符串)中存不存在另一个串(字符串),并返回找到的子串(字符串)的起始位置
C库中的方法:
char* strstr(const char *s,const char *str);
2、算法实现
- BF 算法(朴素算法)
- KMP 算法
学习内容:
BF算法、朴素算法
-
思想:以s串的每一个位置为起始,向后和p串进行比较,如果失配,则从下一个位置开始,如果成功,则返回此时的位置。
-
代码:
int BF(char *s,char *p,int pos)
{
if(s==NULL || p==NULL || pos<0) return -1;
int lens=strlen(s);
int lenp=strlen(p);
if(lens-pos < lenp) return -1;
int i=pos;
int j=0;
while( i<lens && j<lenp)
{
if(s[i]==p[j])
{
i++;
j++;
}
else
{
i=i-j+1;
j=0;
}
}
if(i==lens)
return -1;
return i-j;
}
- 效率:时间复杂度O(m*n)、空间复杂度O(1)
KMP算法
- 思想:
-
代码:
void GetNext(char *p,char *next) { p[0]=-1; int lenp=strlen(p); if(strlen(p)<2) return; next[1]=0; int m=1; int k=0; while(m+1<lenp) { if(k==-1 || p[m]==p[k]) { p[++m]=++k; /* p[m+1]=k+1; m++; k++;*/ } else { k=next[k]; /*if(k==-1) { next[m+1]=0; m++; k++; }*/ } } } int KMP(char *s,char *p,int pos) { if(s==NULL || p==NULL || pos<0) return -1; int lens=strlen(s); int lenp=strlen(p); if(lens-pos < lenp || lenp==0) return -1; int i=pos; int j=0; char *next=(char*)malloc(sizeof(char)*lenp); GetNext(p,next); for(int k=0;k<lenp;k++) { printf("%d ",next[k]); } printf("\n"); while( i<lens && j<lenp) { if(j==-1 || s[i]==p[j]) { i++; j++; } else { j=next[j]; /*if(j==-1) { i++; j++; }*/ } } free(next); if(i==lens) return -1; return i-j; }