LeetCode 17 May, Find All Anagrams in a String, 寻找同字母异序的子串

Find All Anagrams in a String

Given a string s and a non-empty string p, find all the start indices of p’s anagrams in s.

Strings consists of lowercase English letters only and the length of both strings s and p will not be larger than 20,100.

The order of output does not matter.

Example 1:

Input:
s: "cbaebabacd", p:"abc"
Output:
[0, 6]

Explanation:
The substring with start index = 0 is "cba", which is an anagram of "abc".
The substring with start index = 6 is "bac", which is an anagram of "abc".

Example 2:

Input:
s: "abab" p: "ab"
Output:
[0, 1, 2]

Explanation:
The substring with start index = 0 is "ab", which is an anagram of "ab".
The substring with start index = 1 is "ba", which is an anagram of "ab".
The substring with start index = 2 is "ab", which is an anagram of "ab".

分析:

此题如果使用最简单的暴力方法即通过循环嵌套,从第一个字符开始遍历字符串,遍历每个字符串的同时遍历其后面length(p)长度的字符串,通过字典或者数组的存储方式,判断该子串是否与目标串p是顺序不同的串。这种方法的时间复杂度是 O ( n 2 ) O(n^2) O(n2).这种方法基本上会造成超时。采用一种滑动窗口的方法可以将时间复杂度缩短到 O ( n ) O(n) O(n)。详细理解可以参考花花酱的YouTube视频解说花花酱。一下Python代码比较容易理解,采用数组代替字典进行判断是否是顺序不同的串。

# 方法一
# Runtime: 108ms
# Memory Usage: 15MB
class Solution:
    def findAnagrams(self, s: str, p: str) -> List[int]:
        dic_p = [0] * 26
        dic_s = [0] * 26
        
        for x in p:
            dic_p[ord(x)-97] += 1
            
        left, right = 0, 0
        result = []
        while right < len(s):
            dic_s[ord(s[right])-97] += 1
            if right - left + 1 < len(p):
                right += 1
            else:
                if dic_p == dic_s:
                    result.append(left)
                    dic_s[ord(s[left])-97] -= 1
                    left += 1
                    right += 1
                else:
                    dic_s[ord(s[left])-97] -= 1
                    left += 1
                    right += 1
        return result
# 方法二

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值