c++重复的字符子串

字符串经典题目:

给定一个非空的字符串,判断他是否由一个子串重复多次构成,给定的字符只有小写英文字母,且长度不超过10000.

示例 1:

  直接记录我学习理解的kmp算法的一种,主要掌握前缀表(next数组)的写,以及匹配子串的思想。

  • 输入: "abab"
  • 输出: True
  • 解释: 可由子字符串 "ab" 重复两次构成。

    示例 2:

  • 输入: "aba"
  • 输出: False

通过计算next数组,我们可以确定字符串的前缀和后缀的最长公共元素。(也就是前缀和)不必纠结这个名词。如果字符串的最后一个字符的next值不为0,并且字符串长度能够被去掉这部分公共元素后的长度整除,那么字符串就是重复子串模式。

主要学习理解的是next数组:

        next数组是KMP(Knuth-Morris-Pratt)算法中用于模式匹配的核心部分。next数组的目的是帮助算法在不匹配时能够“跳跃”到正确的位置,而不是简单地从当前位置重新开始匹配。

next数组的含义

    next数组的每个元素next[i]表示字符串的前i个字符中,最长的相同前缀和后缀的长度。换句话说,它表示在字符串的第i个位置发生不匹配时,我们应该将模式字符串的开始位置回退到哪个位置,以便继续匹配。

  1. 初始化

    • next[0] = 0;:字符串的第一个字符没有前缀,因此最长的相同前缀和后缀长度为0。
  2. 遍历字符串

    • 通过一个循环遍历字符串的每个字符,从第二个字符开始(索引为1)。
  3. 处理不匹配情况

    • 当当前字符不匹配时(即s[i] != s[j]),我们需要找到一个更短的前缀,使得这个前缀和当前位置之后的字符串有相同的后缀。这是通过回退j来实现的,即j = next[j-1]
  4. 更新next数组

    • 如果当前字符匹配(即s[i] == s[j]),则增加j的值,因为此时我们找到了一个更长的相同前缀和后缀。
    • 更新next[i]j的值,表示在第i个位置,最长的相同前缀和后缀的长度。

 理解next数组的构建过程对于理解KMP算法至关重要,因为它是算法能够高效运行的关键。

 代码:

class Solution {
public:
    void getnext( int *next , string &s)
    {
        next[0] = 0;
        int j = 0;
        for(int i = 1; i <s.size();i++)
        {
            while(j > 0 && s[i] != s[j])
            {
                j = next[j-1];
            }
            if(s[i] == s[j])
            {
                j++;
            }
            next[i] = j;
        }
    }
    bool repeatedSubstringPattern(string s) 
    {
        if(s.size() == 0)
        {
            return false;
        }
        int next[s.size()];
        getnext(next,s);
        int len = s.size();
        if(next[len-1] != 0 && len %(len-(next[len-1]))==0)
        {
            return true;
        }
        return false;
    }
};

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值