您的位置:首页 > 其它

带*和?的KMP算法的两种实现方式

2008-12-18 19:51 399 查看
这两个都是我做助教的那个班的两个同学完成的,觉得她们做得不错,故贴出来共享。

第一个同学的实现:

[code]
#include
#include
#include
class String
{
private:
char * str;
int size;
public:
String( char * s );
~String();

int Strlen ( ) { return strlen( this -> str ) ; } //求长度
char & operator [ ] ( int i ) { return str [ i ] ; } //重载下标运算符
};

String::String(char * s)
{
size = strlen(s);
str = new char[size + 1];
assert(str != NULL);
strcpy(str,s);
}
String::~String()
{
delete str;
}
int * Nature(String & P)
{
int len = P.Strlen() ;
assert( len > 0 ) ;
int * N = new int [ len ] ;
assert( N != NULL ) ;
if( P[0] == '*' )
N[ 0 ] = -1 ;
else
N[ 0 ] = 0 ;
int m = 0 ;
int i = 1 ;
while( m < len )
{
while( i < len && P[ i ] != '*')
{
int k = N[ i -1 ] ;
if( P[ i ] == '?' || P[ k+m ] == '?')
N[ i ] = k + 1 ;
else
{
while( k > 0 && P[ i ] != P[ k+m ] && P[ k+m ] != '?')
k = N[ k-1 ] ;
if( P[ i ] == P[ k+m ] || P[ k+m ] == '?')
N[ i ] = k + 1;
else
N[ i ] = 0;
}
i++;
}
while( P[ i ] == '*' )
{
N[ i ] = -1;
i ++ ;
}
m = i;
}
return N ;
}

int KMP( String & Target , String & Pat , int * N , int StartIndex )
{
int i = 0 , count = 0 ;
for( ; i < Pat.Strlen() ; i ++ )
if( Pat[ i ] == '*' )
count ++;
int LastIndex = Target.Strlen() - Pat.Strlen() ;
if( ( LastIndex - StartIndex ) + count < 0 )
return ( -1 ) ;
i = StartIndex ;
int j = 0 ,m = 0 ;

while( N[ j ] == -1 )
{
j ++;
m ++;
}
int n ,k = 0; //n和k 用来记录开始匹配成功的位置
while( i < Target.Strlen() )
{
while( Target[ i ] != Pat[ j ] && Pat[j ] != '?' && j > m )
j = N[ j - 1 ] + m;
if( Pat[j] == Target[i] || Pat[j ] == '?' )
{
k++;
if(k ==1 )
n = i;

j ++ ;
m ++;
}

while( Pat[j] == '*')
{
j++;
m++;
}

if( j == Pat.Strlen() )
{
cout<<"在位置 "<< n <<" 处匹配成功"<
#include
//#include
#include"String.h"
#include

string::string()
{
size=0;
str=NULL;
}

string::string(char* s)
{
assert(s!=NULL);
str=new char[strlen(s)+1];
assert(str);
strcpy(str,s);
size=strlen(str);

}
//析构函数destructor
string::~string()
{
size=0;
}

char* string:: replace(char A,char B)
{
for(int i=0;i0);
int* N=new int [m];
N[0]=0;
assert(N!=0);
for(int i=1;i0 && P.str[j]!='*'&& P.str[j]!='?')
{
j=N[j-1];
}
if( P.str[j]=='*')
{
j=j+1;
while (S.str[i+1]!=P.str[j] && i
#include
void main()
{
int *N;
int n;
//char* P="infinite";
//char* S="infinishinfinfinite";
string P("a*d*f");
string S("sddddasdfhhhjf");
P.print();
S.print();
N=P.Next(P);
n=S.KMP_FindPat (S, P,N,0);
cout<
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: