Offer 驾到,掘友接招!我正在参与2022春招打卡活动,点击查看活动详情。
一、题目描述:
给定一个非空的字符串 s ,检查是否可以通过由它的一个子串重复多次构成。
示例 1:
输入: s = "abab"
输出: true
解释: 可由子串 "ab" 重复两次构成。
示例 2:
输入: s = "aba"
输出: false
示例 3:
输入: s = "abcabcabcabc"
输出: true
解释: 可由子串 "abc" 重复四次构成。 (或子串 "abcabc" 重复两次构成。)
提示:
- 1 <= s.length <= 10^4
- s 由小写英文字母组成
二、思路分析:
我们知道KMP的next数组表达的意思就是最长相同前后缀,所以只要next数组最后一个元素的值大于0则说明这个字符串有重复的字符串,同时最后next的最后一个下标的值就是最长相同前后缀的最大值。故,用 (数组长度-最长相等前后缀的长度) 正好可以被 数组的长度整除,说明有该字符串有重复的子字符串。
三、AC 代码:
func repeatedSubstringPattern(s string) bool {
if len(s)==1{
return false
}
next:=getNext(s)
fmt.Println(next)
if next[len(s)-1]>0&&len(s)%(len(s)-(next[len(s)-1]))==0{/////////判断关键!!!!想了三天。
return true
}
return false
}
func getNext(s string) []int{
next:=make([]int,len(s))
next[0]=0
j:=0
for i:=1;i<len(s);i++{
for j>0&&s[i]!=s[j]{
j=next[j-1]
}
if s[i]==s[j]{
j++
}
next[i]=j
}
return next
}
四、总结:
kmp还是很重要的,需要熟练掌握。
范文参考: