LeetCode 696. 计数二进制子串

32 阅读1分钟

开启掘金成长之旅!这是我参与「掘金日新计划 · 12 月更文挑战」的第25天,点击查看活动详情

1.描述

696. 计数二进制子串 - 力扣(LeetCode) (leetcode-cn.com)

给定一个字符串 s,统计并返回具有相同数量 0 和 1 的非空(连续)子字符串的数量,并且这些子字符串中的所有 0 和所有 1 都是成组连续的。

重复出现(不同位置)的子串也要统计它们出现的次数。

  示例 1:

输入:s = "00110011"
输出:6
解释:6 个子串满足具有相同数量的连续 10"0011""01""1100""10""0011""01" 。
注意,一些重复出现的子串(不同位置)要统计它们出现的次数。
另外,"00110011" 不是有效的子串,因为所有的 0(还有 1 )没有组合在一起。

示例 2:

输入:s = "10101"
输出:4
解释:有 4 个子串:"10""01""10""01" ,具有相同数量的连续 10

提示:

  • 1 <= s.length <= 10^5
  • s[i] 为 '0' 或 '1'

2.分析

只计算连续字符长度的计数都可以套用此种模板,可以很方便的计算当前字符的连续长度

  1. cur变量存储当前1或0的数量,pre存储上一次的1或0的数量,last存储上次的字符种类用来做计数条件
  2. 当前字符与上次的字符不一样的时候,停止计数,累加最小的0或1的数量,cur的值赋给pre,cur置零重新计数
  3. 最后一段连续长度计算完后跳出循环 ,if条件语句里的累加不会被执行,所以循环结束后还需要再累加一次

3.AC代码

class Solution:
    def countBinarySubstrings(self, s: str) -> int:
        cur = 0
        pre = 0
        last = '_'
        ans = 0
        for i in s:
            if last != i:
                last = i
                ans += min(pre, cur)
                pre = cur
                cur = 0
            cur += 1
        ans += min(cur, pre)
        return ans

参考

【计数二进制子串】计数 - 计数二进制子串 - 力扣(LeetCode) (leetcode-cn.com)

2种解题思路:第2种在第1种的情况下优化了空间复杂度并简化了代码 - 计数二进制子串 - 力扣(LeetCode) (leetcode-cn.com)