KMP算法以及简单应用(查找单词)

来源:互联网 发布:小红帽q群优化软件 编辑:程序博客网 时间:2024/06/05 18:05

上学期在重新学数据结构时,看到匹配算法时,看不懂,然后没时间去研究它,暂时放了下来,早段时间重新研究了 经典的KMP算法,终于搞懂了,自己写了一个kmp算法,并利用它进行了简单的应用,查找单词;例如

Input A string as the Object string..
sdfgdsgsdgr
Input A string as the search string..
sd
Total Count Is ..2
0
7
Press any key to continue

源文件cpp文件:

#include"NewKmp.h"

void main()
{
/* string str = "aaaaaaa15";
 int next[10];
 KMP_Next(str,next);

 for(int i = 0;i<str.size();i++)
 {
  cout<<(str.c_str())[i];
 }
 cout<<endl;
  for(i = 0;i<str.size();i++)
 {
  cout<<next[i];
 }
 cout<<endl;*/

 string S,P;
 int Count;
 vector<int> Vec_Pos;
 cout<<"Input A string as the Object string.."<<endl;
 cin>>S;
 cout<<"Input A string as the search string.."<<endl;
 cin>>P;

/* KMP(S,P,Pos);
 cout<<"The Position Is.. "<<Pos<<endl;*/
 Count_Word(S,P,Count,Vec_Pos);
 cout<<"Total Count Is .."<<Count<<endl;
 for(int i = 0;i<Count;i++)
 {
  cout<<Vec_Pos[i]<<endl;
 }
}

头文件NewKmp.h

#include<iostream>
#include<string>
#include<vector>
using namespace std;

void KMP_Next(const string &str,int next[])
{
 int size = str.size();
 int j = 1;
 int k = 0;
 next[0] = 0;
 next[1] = 0;

 while(j<size)
 {
  if((str.c_str())[j] == (str.c_str())[k])
  {
   next[j+1] = k+1;
   j++;
   k = next[j];
  }
  else
  { 
   while(k>0)    //递推查找
   {
    k = next[k];
   }    
   if((str.c_str())[j] != (str.c_str())[k])  //是否与首字符相等
   {
    next[j+1] = 0;
    j++;
   }
  
  }
 }
}

void KMP(const string &S,const string &P,int &Pos)
{
 int j = 0;
 int i = 0;
 int next[10];
 KMP_Next(P,next);
 bool UPDATE = false;
 while(j<S.size())
 {
  if((S.c_str())[j] == (P.c_str())[i])
  {
   if(i == P.size()-1)
   {
    Pos = j-P.size()+1;
    UPDATE = true;
    break;
   }
   j++;
   i++;
  }
  else
  {
   if(i == 0)
   {
    j++;
   }
   else
   {
    i = next[i];
   }
  }
 }
 if(UPDATE == false)
 {
  Pos = -1;
 }
}

void Count_Word(const string &S,const string &C,int &Count,vector<int> &Vec_Pos)
{
 int i = 0;
 Count = 0;        //初始化Count
 int Pos = -1;  //初始化
 int Pre_Pos = 0; //记住前一次的位置
 string t_str = S; //用于循环S查找串的临时变量
 while(i<S.size())
 {
  t_str = t_str.substr(i); //剪接
  KMP(t_str,C,Pos);   //KMP算法 
  if(Pos>=0)
  {
   Count++;
   Vec_Pos.push_back(Pre_Pos+Pos);  //记录位置
   i = Pos+C.size();
   Pre_Pos = i+Pre_Pos;   //定位下一次
  } 
  else
  {
   break;
  }
 }
}

 

原创粉丝点击