20. 有效的括号

204 阅读2分钟

给定一个只包括 '(',')''{','}''[',']' 的字符串 s ,判断字符串是否有效。

有效字符串需满足: 左括号必须用相同类型的右括号闭合。 左括号必须以正确的顺序闭合。

示例 1:
输入:s = "()"
输出:true

示例 2:
输入:s = "()[]{}"
输出:true

示例 3:
输入:s = "(]"
输出:false

示例 4:
输入:s = "([)]"
输出:false

解法一

自己看答案前,自己的解法,一次遍历就搞定。

主要思想:用一个数组用于存放左半边的括号,每次遍历遇到右半边括号的时候,看下数组最后一个是不是对应的左半边括号,如果是的话,那么这对括号就匹配,然后移除数组最后一项,继续遍历。

def isValid(s):
    arr = []  # 用于记录的数组
    for ch in s:
        if ch in ("(", "[", "{"):
            arr.append(ch)
        else:
            if len(arr) > 0 and ch == ")" and arr[-1] == "(":
                arr.pop()
            elif len(arr) > 0 and ch == "]" and arr[-1] == "[":
                arr.pop()
            elif len(arr) > 0 and ch == "}" and arr[-1] == "{":
                arr.pop()
            else:
                return False
    return True if len(arr) == 0 else False

解法二

力扣官方答案和我的思想是一样的,都是用的思想,先进后出。 而且官方用了字典,空间复杂度要稍微高一些。

def isValid1(s):
    if len(s) % 2 == 1:
        return False

    pairs = {
        ")": "(",
        "]": "[",
        "}": "{",
    }
    stack = list()
    for ch in s:
        if ch in pairs:
            # not stack 的意思是:如果还有右括号,但是左括号没有了的情况
            if not stack or stack[-1] != pairs[ch]:
                return False
            stack.pop()  # 括号匹配的话,就移除栈顶
        else:
            stack.append(ch)  # 添加左括号

    return not stack
复杂度分析
  • 时间复杂度:O(n)O(n)
  • 空间复杂度:解法一的空间复杂度就是数组的长度,最坏的情况全是左括号,是O(n)O(n)。解法二的空间复杂度就是数组的长度加上字典的长度,是O(n+Σ)O(n+∣Σ∣),其中 ΣΣ 表示字符集,本题中字符串只包含 6 种括号,Σ=6∣Σ∣=6