这道题是字符串匹配问题,第一反应当然是KMP算法和BF算法,虽然前两天刚学了KMP,自己动手写还是不会写next数组。按自己思路写了双指针算法,虽然提交通过,但是代码质量极差可以称为垃圾代码…,运行时间1960ms…
#include "iostream"
#include "string"
using namespace std;
class Solution {
public:
int strStr(string haystack, string needle) {
if(needle.length()==0||needle==haystack)return 0;
if(needle.length()>haystack.length())return -1;
int i;
for(i=0;i
偷个懒,调函数。
#include "iostream"
#include "string"
using namespace std;
class Solution {
public:
int strStr(string haystack, string needle) {
if(needle.empty()) return 0;
else
{
int pos=haystack.find (needle);
return pos;
}
return -1;
}
};
暴力解法,但比我的代码高效的多,匹配成功时,各自+1,比较下一位。匹配失败下标就要回溯,对于needle串,要回溯到0的位置,对于Haystack串,则返回到i-j+1的位置。
#include "iostream"
#include "string"
using namespace std;
class Solution {
public:
int strStr(string haystack, string needle) {
//加几个很好想到的特殊情况,加快判断
if(needle.empty() || needle==haystack ) return 0;
if(needle.length()>haystack.length()) return -1;
int i=0,j=0;
while(needle[i]!='\0' && haystack[j] !='\0')
{
if(needle[i] ==haystack[j])
{
i++;
j++;
}
else //回溯
{
//haystack从上次匹配的下一位开始 needle从头开始
j=j-i+1;
i=0;
}
}
if(needle[i]=='\0') return j-i;
else return -1;
}
};
class Solution {
public:
vector getnext(string str)
{
int len=str.size();
vector next;
next.push_back(-1);//next数组初值为-1
int j=0,k=-1;
while(j next;
next=getnext(needle);
while((i
next数组可以进行优化,当字符失配时,回到相同字符无意义,应继续递归。
vector getnext(string str)
{
int len=str.size();
vector next;
next.push_back(-1);//next数组初值为-1
int j=0,k=-1;
while(j
以下几种算法来自
https://leetcode-cn.com/problems/implement-strstr/solution/c5chong-jie-fa-ku-han-shu-bfkmpbmsunday-by-2227/
的总结,还没有很理解,先收藏进来。
class Solution {
public:
void get_bmB(string& T,vector& bmB)//坏字符
{
int tlen=T.size();
for(int i=0;i<256;i++)//不匹配直接移动子串
{
bmB.push_back(tlen);
}
for(int i=0;i& suff)
{
int tlen=T.size();
int k;
for(int i=tlen-2;i>=0;i--)
{
k=i;
while(k>=0&&T[k]==T[tlen-1-i+k])
k--;
suff[i]=i-k;
}
}
void get_bmG(string& T,vector& bmG)//好后缀
{
int i,j;
int tlen=T.size();
vector suff(tlen+1,0);
get_suff(T,suff);//suff存储子串的最长匹配长度
//初始化 当没有好后缀也没有公共前缀时
for(i=0;i=0;i--)
if(suff[i]==i+1)
for(j=0;j bmG (tlen,0);
vector bmB;
get_bmB(needle,bmB);
get_bmG(needle,bmG);
while(i<=slen-tlen)
{
for(j=tlen-1;j>-1&&haystack[i+j]==needle[j];j--);
if(j==(-1))
return i;
i+=max(bmG[j],bmB[haystack[i+j]]- (tlen-1-j));
}
return -1;
}
};
class Solution {
public:
int strStr(string haystack, string needle) {
if(needle.empty())
return 0;
int slen=haystack.size();
int tlen=needle.size();
int i=0,j=0;//i指向源串首位 j指向子串首位
int k;
int m=tlen;//第一次匹配时 源串中参与匹配的元素的下一位
for(;i=0;k--)//遍历查找此时子串与源串[i+tlen+1]相等的最右位置
{
if(needle[k]==haystack[m])
break;
}
i=m-k;//i为下一次匹配源串开始首位 Sunday算法核心:最大限度跳过相同元素
j=0;//j依然为子串首位
m=i+tlen;//m为下一次参与匹配的源串最后一位元素的下一位
if(m>slen)//当下一次参与匹配的源串字数的最后一位的下一位超过源串长度时
return -1;
}
else
{
if(j==tlen-1)//若j为子串末位 匹配成功 返回源串此时匹配首位
return i-j;
i++;
j++;
}
}
return -1;//当超过源串长度时
}
};