KMP算法

5 篇文章 0 订阅

题:
对于两个字符串A,B。请设计一个高效算法,找到B在A中第一次出现的起始位置。若B未在A中出现,则返回-1。
给定两个字符串A和B,及它们的长度lena和lenb,请返回题目所求的答案。

例:
“acbc”,4,”bc”,2
返回:2

思:
next数组的获取,当前位置为cur
cur-2位置结尾的某个字符串

字符串开头到preEnd-1位置是相等的字符串,
则只需匹配cur-1和preEnd是否相等

码:

vector<int> getNextArray(const string &str){    
    vector<int> next(str.size());
    if(str.size()==0)
        return next;
    next[0]=-1;
    if(str.size()==1)
        return next;
    next[1]=0;
    int pos=2;//当前位置
    int preEnd=0;//
    while(pos<next.size()){
        if(str[pos-1]==str[preEnd])//看前面位置
            next[pos++]=++preEnd;
        else if(preEnd>0)
            preEnd=next[preEnd];
        else
            next[pos++]=0;
    }
    return next;
}

int findAppearance(string A, int lena, string B, int lenb) {    
    if(lenb==0)
        return 0;
    if(lenb<0||lena<0||lenb>lena)
        return -1;
    vector<int> next=getNextArray(B);
    int j=0;
    int i=0;
    for(;i<lena&&j<lenb;){
        int oldi=i;
        if(A[i]==B[j]){
            i++;
            j++;
        }else if(next[j]==-1){//已经匹配所有,只能跳过这个字符,j==0
            i++;
        }else
            j=next[j];        
    }
    return j==lenb?i-lenb:-1;
}

测:

int main(){
    string strs="syyasyybcd";//-1,0,0,0,0,1,2,3,0,0
    string strl="fdfasfdsfs"                
                "syyasyybcd"
                "fasdfasfad";
    cout<<findAppearance(strl,strl.size(),strs,strs.size());
    return 0;
}

源:
https://www.nowcoder.com/practice/084b6cb2ca934d7daad55355b4445f8a?tpId=49&tqId=29363&tPage=5&rp=5&ru=/ta/2016test&qru=/ta/2016test/question-ranking

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值