[代码随想录算法训练营 Day09 字符串 Part2]

Day 09

字符串

今天两道KMP:KMP功能,在一个字符串中找到是否出现另一个字符串
本篇会再更新~

6. 实现strStr(力扣28)

  1. 题目描述:找出字符串中第一个匹配项的下标heystack干草堆,needle针,大海捞针~
  2. 思路:KMP算法
  • B站一个讲的很好的视频
  • 整体思路:假设有主串n和模式串m,在暴力算法当中,每当主串与模式串不匹配,我们就需要对主串和模式串同时回溯,时间复杂度为O(n*m)
  • 可以改进的地方在于:当我匹配到模式串的某个部分不同时,我就无需重全部从头遍历:当主串匹配到A,从串匹配到C,起码来讲,主串一定是经历过AB的,这个AB在我接下来要匹配的时候,可以和模式串的开头AB对应上,所以我就看看下一个和开头AB的后一个能不能对应上。(看不懂就看看视频)
    在这里插入图片描述
  1. python语法细节
  2. python实现
class Solution:
    def strStr(self, haystack: str, needle: str) -> int:
        next_ = [None]*len(needle)
        self.build_next(next_,needle)
        i=0
        j=0
        while i<=len(haystack):
            if(j==len(needle)):
                return i-len(needle)
            elif(i == len(haystack)):
                return -1             
            elif(haystack[i]==needle[j]):
                # print(i,j)
                i +=1
                j+=1
            else:
                if(j==0):
                    i+=1
                else:j = next_[j-1]

    def build_next(self,next,s):
        #首个字符串的最长公共前缀为0,直接赋值
        next[0]=0
        max_prex = 0
        #首个字符记过了,我们从第二个字符开始,下标为1
        i = 1
        #i不回溯,因此算法的时间复杂度为O(N)
        while i<len(s):
            #i遍历到的待求解字符和当前最长前缀的下一个字符相等时
            if(s[i]==s[max_prex]):
                #那么i的最长前缀就是当前最长前缀+1
                next[i]=max_prex+1
                #可以遍历下一个数了
                i+=1
                #当前最长前缀长度+1了哦
                max_prex+=1
            #i遍历到的带求解字符和当前最长前缀的下一个字符不等
            #那就在这个前缀上找找关系,这一小块也不白遍历,利用一下前缀中的重复元素
            else:
                #都找到第一个元素了,都没重复的,那就是0了
                if max_prex == 0:
                    next[i]=0
                    #遍历下一个数
                    i+=1
                else:
                    #m没到0就还能抢救一下,再看看前缀里有没有重复元素
                    max_prex = next[max_prex-1]

7. 重复的子字符串(力扣459)

  1. 题目描述:
  2. 思路:这道题可以理解为:从1到中部这些位置开始的字符串,是否有可能包含从0开始的字符串。因此我们还是先求s的next数组(其实求一半就行,因为子串不可能比一半还长)。然后以1开头作为主串进行遍历,如果相同就主串子串同时向后,如果不同,那么子串不用全部回溯到0,只需要回溯到next数组说的值就可以。最终判断,right-left就是子串长度,如果left可以被长度整出,就位真。
  3. python语法细节:
  4. python实现:
class Solution:
    def repeatedSubstringPattern(self, s: str) -> bool:
        next_ = [None]*len(s)
        self.build_next(next_,s)
        print(next_)
        if(len(s)==1):
            return False
        left = 0
        right = 1
        while(right<len(s)):
            print(left,right)
            if(s[left]==s[right]):
                left +=1
                right +=1
            
            else:
                if left==0:
                    right+=1
                else:
                    left = next_[left-1]
                  
        l = right - left
        if (l!=0 and left%l==0 and left!=0):
            return True
        else:
            return False
    def build_next(self,next,s):
        i = 1
        max_len = 0
        next[0] = 0
        while(i<len(s)):
            if(s[i]==s[max_len]):
                max_len +=1
                next[i]=max_len
                i +=1
            else:
                if(max_len==0):
                    next[i]=0
                    i+=1
                else:
                    max_len = next[max_len-1]
  • 5
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
代码随想录算法训练营是一个优质的学习和讨论平台,提供了丰富的算法训练内容和讨论交流机会。在训练营中,学员们可以通过观看视频讲解来学习算法知识,并根据讲解内容进行刷题练习。此外,训练营还提供了刷题建议,例如先看视频、了解自己所使用的编程语言、使用日志等方法来提高刷题效果和语言掌握程度。 训练营中的讨论内容非常丰富,涵盖了各种算法知识点和解题方法。例如,在第14天的训练营中,讲解了二叉树的理论基础、递归遍历、迭代遍历和统一遍历的内容。此外,在讨论中还分享了相关的博客文章和配图,帮助学员更好地理解和掌握二叉树的遍历方法。 训练营还提供了每日的讨论知识点,例如在第15天的讨论中,介绍了层序遍历的方法和使用队列来模拟一层一层遍历的效果。在第16天的讨论中,重点讨论了如何进行调试(debug)的方法,认为掌握调试技巧可以帮助学员更好地解决问题和写出正确的算法代码。 总之,代码随想录算法训练营是一个提供优质学习和讨论环境的平台,可以帮助学员系统地学习算法知识,并提供了丰富的讨论内容和刷题建议来提高算法编程能力。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* *2* *3* [代码随想录算法训练营每日精华](https://blog.csdn.net/weixin_38556197/article/details/128462133)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 100%"] [ .reference_list ]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值