持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第22天,点击查看活动详情
说明:文章部分内容及图片出自网络,如有侵权请与我本人联系(主页有公众号:小攻城狮学前端)
作者:小只前端攻城狮、 主页:小只前端攻城狮的主页、 来源:掘金
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
【LeetCode 1541. 平衡括号字符串的最少插入次数 】- JavaScript(栈模拟)
题目描述
给你一个括号字符串 s ,它只包含字符 '(' 和 ')' 。一个括号字符串被称为平衡的当它满足:
任何左括号 '(' 必须对应两个连续的右括号 '))' 。
左括号 '(' 必须在对应的连续两个右括号 '))' 之前。
比方说 "())", "())(())))" 和 "(())())))" 都是平衡的, ")()", "()))" 和 "(()))" 都是不平衡的。
你可以在任意位置插入字符 '(' 和 ')' 使字符串平衡。
请你返回让 s 平衡的最少插入次数。
示例 1:
输入:s = "(()))" 输出:1 解释:第二个左括号有与之匹配的两个右括号,但是第一个左括号只有一个右括号。我们需要在字符串结尾额外增加一个 ')' 使字符串变成平衡字符串 "(())))" 。
栈
思路分析:
栈的思路:依旧是对字符串进行遍历,从右往左遍历字符串,通过设置count变量来记录右括号‘)’的数量,如果遇到左括号时就进行count变量-2,但是要注意这几点:
- 对遍历的第一个括号时操作数时,进行特判。
- 遍历时遇到到左括号时且当右边落单右括号时,进行的处理是‘()))’
- 遍历时遇到到左括号时对右边夹缝中右括号的处理是‘()(’
- 左括号对应的右括号一定要是偶数,即左括号必须在对应的连续两个右括号之前
- 如果为奇数, 表明此时需要插入一个右括号,如果左括号不足,那么补1;
这个题有个坑就是再出现一组连续括号的后,开始我以为是要将这组括号都匹配完,最后发现只需要匹配完右括号,左括号可以向后保留。
var minInsertions = function(s) {
let len = s.length,
stack = [],
res = 0
for(let i = 0; i < len; i++) {
if(s[i] == '(') {
stack.push('(')
continue
}
if(i + 1 == len) {
if(stack.length == 0) res += 2
else {
res++
stack.pop()
}
}else {
if(s[i+1] == ')') {
if(stack.length == 0) res++
else stack.pop()
i++
}else {
if(stack.length == 0) res += 2
else {
res++
stack.pop()
}
}
}
}
res += stack.length * 2
return res
};
思考
其实这个题目用栈模拟是最后的方法,当前其他方法也是可以做的,但是栈的方式更容易的理解和处理,时间复杂度也很低。虽然用栈的,但是可以正向模拟,也可以逆向模拟,即既可以埋点count数量进行减减,或者模拟操作数据正向增加。
感谢阅读,希望能对你有所帮助,文章若有错误或者侵权,可以在评论区留言或在我的主页添加公众号联系我。
写作不易,如果觉得不错,可以「点赞」+「评论」 谢谢支持❤