SDIBT 2696 KMP模式匹配 一(串)
Description
求子串的next值,用next数组存放,全部输出
Input
输入一个字符串
Output
输出所有next值
Sample Input
abaabcac
Sample Output
0 1 1 2 2 3 1 2
#include<cstring>
#include<iostream>
using namespace std;
int main ()
{
int next[2000];
char p[2000];
int j,k;
next[0]=-1;
j=0;
k=-1;
cin>>p;
int len=strlen(p);
while(j<len-1){
if(k==-1||p[j]==p[k]){ //匹配的情况下,p[j]==p[k]
j++;
k++;
next[j]=k;
}
else //p[j]!=p[k]
k=next[k];
}
int i;
for(i=0;i<len-1;i++)
cout<<next[i]+1<<' ';
cout<<next[i]+1;
return 0;
}
next数组产生过程辅助理解:
#include<cstring>
#include<iostream>
using namespace std;
int main ()
{
while(1){
int next[2000];
char p[2000];
int j,k;
next[0]=-1;
j=0;
k=-1;
cout<<"输入为:";
cin>>p;
int len=strlen(p);
cout<<endl<<"执行过程:"<<endl;
while(j<len-1)//len-1是因为后面有个j++
{
if(k==-1||p[j]==p[k]) //匹配的情况下,p[j]==p[k]
{
cout<<"进入if语句:"<<endl;
j++; //递推因子只在这里加
cout<<"j++="<<j<<endl;
k++;
cout<<"k++="<<k<<endl;
next[j]=k;
cout<<"next["<<j<<"]="<<k<<endl<<endl;
}
else { //p[j]!=p[k]
cout<<"进入else语句:"<<endl;
int temp=k;
k=next[k];
cout<<"k="<<next[temp]<<endl<<endl;
}
}
cout<<"获得的next数组为:"<<endl;
int i;
for(i=0;i<len-1;i++) //len-1是因为后面有个
cout<<next[i]<<' ';
cout<<next[i]<<endl;
}
return 0;
}
运行情况:
最后实例结合:http://blog.csdn.net/u014665013/article/details/38985621
SDIBT 2697 KMP模式匹配 二(串)
Description
输入一个主串和一个子串,用KMP进行匹配,问进行几趟匹配才成功,若没成功,则输出0
Input
输入一个主串和一个子串
Output
匹配的趟数
Sample Input
ababcabcacbab
abcac
Sample Output
3
#include<iostream>
#include<string>
#include<cstring>
using namespace std;
const int maxsize=100;
void getnext(string t,int next[])//此处也可以将int next[]改写成 int* next[]
{
int j,k;
j=0; k=-1; next[0]=-1;
while(j<t.length()-1){
if(k==-1 ||t[j]==t[k]){
j++;k++;
next[j]=k;
}
else k=next[k];
}
}
int kmpindex(string s,string t)//s为目标串(主串),t为模式串
{
int next[maxsize],i=0,j=0;
//memset(next,-1,sizeof(next));
getnext(t,next);
int m=0;
m++;
int s_len=s.length(),t_len=t.length();//此处注意返回值得问题,详见:<a target=_blank href="http://blog.csdn.net/u014665013/article/details/38292717">http://blog.csdn.net/u014665013/article/details/38292717</a>
while(i<s_len && j<t_len){
if(j==-1 ||s[i]==t[j]){
i++;
j++;
}
else
j=next[j],m++;
}
if(j>=int(t.length() ))
return m;
else
return 0;
}
int main()
{
string a;
string b;
cin>>a;
cin>>b;
cout<<kmpindex(a,b)<<endl;
return 0;
}
SDIBT 2698 KMP模式匹配 三(串)
Description
输入一个主串和一个子串,若匹配成功,则找出匹配的趟数和在子串在主串中的位置,若匹配不成功,则输出0
Input
输入两个字符串
Output
输出匹配的趟数和位置
Sample Input
ababcabcacbab
abcac
Sample Output
3 6
#include<iostream>
#include<string>
#include<cstring>
using namespace std;
const int maxsize=100;
void getnext(string t,int next[])
{
int j,k;
j=0; k=-1; next[0]=-1;
while(j<t.length()-1){
if(k==-1 ||t[j]==t[k]){
j++;k++;
next[j]=k;
}
else k=next[k];
}
}
void kmpindex(string s,string t)
{
int next[maxsize],i=0,j=0;
memset(next,-1,sizeof(next));
getnext(t,next);
int m=0;
m++;
while(i<s.length() &&j<int(t.length())){
if(j==-1 ||s[i]==t[j]){
i++;
j++;
}
else j=next[j],m++;
}
if(j>=int(t.length() ))
cout<<m<<' '<<(i-t.length())+1<<endl;;
else
cout<<0<<endl;
}
int main()
{
string a;
string b;
cin>>a;
cin>>b;
kmpindex(a,b);
return 0;
}