LeetCode 1249 移除无效的括号

83 阅读1分钟

参加了 kkb 的门徒培训,想要记录下自己的成长过程。每天一篇,坚持不断更 --- 2022.3.24

题目描述

给你一个由 '('')' 和小写字母组成的字符串 s

你需要从字符串中删除最少数目的 '(' 或者 ')' (可以删除任意位置的括号),使得剩下的「括号字符串」有效。

请返回任意一个合法字符串。

有效「括号字符串」应当符合以下 任意一条 要求:

  • 空字符串或只包含小写字母的字符串
  • 可以被写作 ABA 连接 B)的字符串,其中 A 和 B 都是有效「括号字符串」
  • 可以被写作 (A) 的字符串,其中 A 是一个有效的「括号字符串」

 

示例 1:

输入: s = "lee(t(c)o)de)"
输出: "lee(t(c)o)de"
解释: "lee(t(co)de)" , "lee(t(c)ode)" 也是一个可行答案。

示例 2:

输入: s = "a)b(c)d"
输出: "ab(c)d"

示例 3:

输入: s = "))(("
输出: ""
解释: 空字符串也是有效的

 

提示:

  • 1 <= s.length <= 105
  • s[i] 可能是 '('')' 或英文小写字母

解题思路

利用栈保存字符,并记录 '(' 数量

/**
 * @param {string} s
 * @return {string}
 */
var minRemoveToMakeValid = function(s) {
    // 用一个栈标记需要删除位置,当记录完成后转换成字符串
    let n = 0;
    const needRemove = [];

    for (let i in s) {
        const str = s[i]
        if (str == "(") {
          needRemove.push(i);
          n++;
        } 
        else if (str == ")") {
          // 判断是否之前是否存在 "("
          if (n > 0) {
            needRemove.pop();
            n--;
          } 
          else {
            needRemove.push(i);
          }
        }
    }

    if (!needRemove.length) return s;

    let ans = '';
    for (let i in s) {
        if (needRemove[0] === i) {
            needRemove.shift()
        }
        else ans += s[i];
    }
    return ans;
};