首页
学习
活动
专区
圈层
工具
发布
社区首页 >专栏 >有效的括号(leetcode 20)

有效的括号(leetcode 20)

作者头像
恋喵大鲤鱼
发布2022-09-27 21:05:35
发布2022-09-27 21:05:35
3020
举报
文章被收录于专栏:C/C++基础C/C++基础

文章目录

1.问题描述

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

有效字符串需满足:

  • 左括号必须用相同类型的右括号闭合。
  • 左括号必须以正确的顺序闭合。
  • 每个右括号都有一个对应的相同类型的左括号。

示例 1:

代码语言:javascript
复制
输入:s = "()"
输出:true

示例 2:

代码语言:javascript
复制
输入:s = "()[]{}"
输出:true

示例 3:

代码语言:javascript
复制
输入:"{[]}"
输出:true

示例 4:

代码语言:javascript
复制
输入:s = "(]"
输出:false

示例 5:

代码语言:javascript
复制
输入:s = "([)]"
输出:false

2.难度等级

easy。

3.热门指数

★★★★☆

出题公司:深圳云摩科技、bilibili

4.解题思路

捋清什么是有效字符串,那么解题思路便浮出水面。

遍历给定的字符串 s,当遇到一个左括号时,我们会期望在后续的遍历中,有一个相同类型的右括号与其闭合。在遇到对应的右括号之前,有两种情况:

  • 一种是下一个相邻的就是对应的右括号,如 ()[]{};
  • 一种是会有其他的括号,那么被包裹的子串也需要是有效字符串,如 ([]{})。

如果不满足上面的要求,就是无效的字符串。

知道了什么是效字符串后,我们会发现其有一个特性,所有成对字符串都可以被 “消除”。如果遍历完后有剩余字符,那么说明其是无效字符串。整个过程有点像玩俄罗斯方块,最后全部被消除说明是有效字符串,反之便是无效字符串。

比如遍历 ([]{}):

代码语言:javascript
复制
(
([
([]  // [] 成对消除后继续遍历
({
({} // {} 成对消除后继续遍历
()  // () 成对消除后遍历完毕

如何实现上面遍历消除的过程呢?因为消除的成对括号都在最右边,所以我们可以使用来实现。将遍历左括号入栈,遇到右括号时判断其与栈顶的左括号能否成对,如果成对则将左括号出栈,如果不成对,则直接返回 False。遍历完成后,栈如果是空的则是有效字符串,反之为无效字符串。

注意到有效字符串的长度一定为偶数,因此如果字符串的长度为奇数,我们可以直接返回 False,省去后续的遍历判断过程。

复杂度分析:

时间复杂度:O(n),其中 n 是字符串的长度。

空间复杂度:O(n/2),栈中最多保留全部的左括号。

5.实现示例

5.1 C++

代码语言:javascript
复制
#include <stack>

// isValid 是否为有效字符串。
bool isValid(string s) {
  int n = s.size();
  if (n % 2 == 1) {
    return false;
  }

  stack<char> stk;
  for (char c : s) {
    if (c == '(' || c == '[' || c == '{') {
      stk.push(c);
      continue;
    }
    // 必须有左括号在栈中。
    if (stk.empty()) {
      return false;
    }
    switch (c) {
    case ')':
      if (stk.top() != '(') {
        return false;
      }
      break;
    case ']':
      if (stk.top() != '[') {
        return false;
      }
      break;
    case '}':
      if (stk.top() != '{') {
        return false;
      }
      break;
    }
    stk.pop();
  }
  return stk.empty();
}

5.2 Golang

代码语言:javascript
复制
// isValid 是否为有效字符串。
func isValid(s string) bool {
    n := len(s)
    if n % 2 == 1 {
        return false
    }
    var stack []rune
    for _, c := range s {
        if c == '(' || c == '[' || c == '{' {
            stack = append(stack, c)
            continue
        }
        // 必须有左括号在栈中。
        if len(stack) == 0 {
            return false
        }
        switch c {
        case ')':
            if stack[len(stack)-1] != '(' {
                return false
            }
        case ']':
            if stack[len(stack)-1] != '[' {
                return false
            }
        case '}':
            if stack[len(stack)-1] != '{' {
                return false
            }
        }
        stack = stack[:len(stack)-1]
    }
    return len(stack) == 0
}

参考文献

20. 有效的括号 - leetcode

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2022-09-14,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 文章目录
  • 1.问题描述
  • 2.难度等级
  • 3.热门指数
  • 4.解题思路
  • 5.实现示例
    • 5.1 C++
    • 5.2 Golang
  • 参考文献
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档