【力扣刷题记 20】——《有效的括号》

144 阅读2分钟

Offer 驾到,掘友接招!我正在参与 2022 春招打卡活动,点击查看活动详情

一、题目描述:

  1. 有效的括号-难度简单 给定一个只包括 '(',')','{','}','[',']' 的字符串 s ,判断字符串是否有效。

有效字符串需满足:

左括号必须用相同类型的右括号闭合。 左括号必须以正确的顺序闭合。  

示例 1:

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

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

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

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

输入:s = "{[]}" 输出:true  

提示:

1 <= s.length <= 104 s 仅由括号 '()[]{}' 组成

二、题目和思路分析:

最最开始我想的很简单:

如果字符串有效,那么括号必定不能互相交叉

也就是说,这道题本质上是考察回文

所以判断条件为:

  1. 字符串长度为偶数

  2. 将字符串一分为二,翻转第一部分,它和第二部分完全相等

可是当我开始写代码,我发现我想的并不正确:

一分为二判断两边完全相等是错误的,左括号翻转也不会变成右括号,并且两边也不一定完全相等

于是我想了想,判断条件应该是:

  1. 每一对括号里都不能只存在其它单个的括号

  2. 每个左括号都有按顺序与之对应的右括号

可是这么想代码还是无从下手。。。

终于在我手动写了n个测试例子之后,我才明白过来:

最开始的字符必定是左括号,遇到第一个右括号,与之对应的左括号一定是前面所遇到的最后一个左括号。

这么想起来,一切就很简单起来了~

三、代码:

代码实现如下:

/**
 * @param {string} s
 * @return {boolean}
 */
var isValid = function(s) {
    if(s.length%2 == 1){ // 如果是奇数,直接返回false
        return false
    }else{
        let arr = [] // 记录遇到的左括号
        let obj = { // 括号对应关系
            '(': ')',
            '[': ']',
            '{': '}',
        }
        for(let x of s) { // 遍历s字符串
            if(x in obj) { // 如果是左括号,加入到arr
                arr.push(x)
                continue
            }
            if(obj[arr.pop()] !== x){ // 如果是右括号,则取出左括号数组的最后一项看是否对应,如果不对应当前左括号的最后一项,则返回false
            // pop()方法删除数组的最后一项,返回数组的最后一项,并改变原数组。
                return false
            }
        }
        return arr.length == 0 // 当数组完全被对应消除完,才算正确
    }
}



四、总结:

这道题写的简,看起来也挺简单,但是做起来还是感觉有点难度,主要是规律不好把握。

所以对于这道题而言,难的不是代码的逻辑,而是解决的方法思路,即:【遇到第一个右括号,与之对应的左括号一定是前面所遇到的最后一个左括号。】

加油吧!

image.png