打卡Day9

本文详细介绍了KMP算法中的next数组构造过程,包括初始化、处理前后缀不相同和相同情况,以及在实际问题如查找子串和重复子字符串中的应用。作者反思了对算法的理解误区并强调了模拟代码运行的重要性。
摘要由CSDN通过智能技术生成

前言:kmp算法

今天又温习了一遍kmp算法(为什么自己学一次忘一次呢。。。)

求next数组有4个步骤:

1.初始化next数组

2.处理前后缀不相同的情况

3.处理前后缀相同的情况

4.更新next数组

我发现我之前手写kmp数组的时候好像一直有一个错误,不知道是不是因为听的网课对模式串作了特殊处理的缘故;例如对于aabaaab字符串,默认next[0] = 0 ,是因为对于‘a’,没有前后缀;

aabaaab

0

然后填next[1]的时候,应该直接看“aa”,所以next[1] = 1;之前一直以为不能算上当前字母。。。

28.找出字符串中第一个匹配项的下标

题目内容:给你两个字符串 haystack 和 needle ,请你在 haystack 字符串中找出 needle 字符串的第一个匹配项的下标(下标从 0 开始)。如果 needle 不是 haystack 的一部分,则返回  -1 

我的代码

class Solution {
public:
    void get_next(vector<int>& next, string s) 
    {
        next[0] = 0;
        int i = 1, j = 0;  //i为后缀末尾,j为前缀末尾
        for( ; i < s.size(); i++) {
            while((s[i] != s[j]) && j > 0) {
                j = next[j - 1];
            }
            if(s[i] == s[j]) {
                j++;
                
            }
            next[i] = j;
        }
    }
    int strStr(string haystack, string needle) {
        if(needle.size() == 0) return -1;
        vector<int> next(needle.size(), 0);
        get_next(next, needle);
        int i = 0, j = 0;
        for( ; i < haystack.size(); i++) {
            while((haystack[i] != needle[j]) && j > 0) {
                j = next[j - 1];
            }
            if(haystack[i] == needle[j]) {
                
                j++;
            }
            if(j == needle.size()) {
                return (i - j + 1);
            }
        }
        return -1;
    }
};

反思:一道很经典的kmp算法题了。求next数组的时候,要注意,当前后缀不相等时,前缀末尾j要持续回退至0或回退至前后缀相等,这样才能得到正确的next[i]的值;在正式求下标的时候也是同理,两字符不相等时,j一直回退到头头或者回退至两字符相等,这样才能继续判断;返回下标时注意不直接返回i,因为i此时已经指向了子字符串的末尾,而题目要求的是子字符串在主串中出现的第一个下标,因此还要再减j的下标,由于此时j已经走到了子串的外面一个,因此还要再+1。

感觉自己对kmp算法运行过程以及为什么这么写还不是很懂,还需要多模拟几次代码运行过程多练练题。

459.重复的子字符串

题目内容:给定一个非空的字符串 s ,检查是否可以通过由它的一个子串重复多次构成。

掐头去尾法代码

class Solution {
public:
    bool repeatedSubstringPattern(string s) {
        string s1 = s + s;
        s1.erase(s1.begin());
        s1.erase(s1.end() - 1);
        if(s1.find(s) != string :: npos) return true;
        return false;
    }
};

思路:如果一个字符串是由一个子串重复多次构成的,那么它复制一遍后,中间一定还能再找到一个子串,但是为了防止找到的子串就是由原来子串拼接而来的子串,需要对复制后的字符串掐头去尾。

kmp算法版先欠着吧,今晚感觉脑容量爆炸了。QAQ

  • 5
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值