LeetCode22:括号生成

原题地址:. - 力扣(LeetCode)

题目描述

数字 n 代表生成括号的对数,请你设计一个函数,用于能够生成所有可能的并且 有效的括号组合。

示例 1:

复制代码
输入:n = 3
输出:["((()))","(()())","(())()","()(())","()()()"]

示例 2:

复制代码
输入:n = 1
输出:["()"]

提示:

  • 1 <= n <= 8

实现思路

题目要求生成所有有效的括号组合。有效的括号组合是指每个左括号 ( 都有对应的右括号 ),且在任意前缀中左括号的数量不少于右括号的数量。

思路:

  1. 回溯法 :使用回溯法生成所有可能的括号组合。可以用一个字符数组 current 来存储当前的组合。
  2. 递归生成:在每个位置上可以选择放入左括号或右括号。
  3. 验证有效性:在生成完整的组合后,通过一个辅助函数检查该组合是否有效。
  4. 结束条件:当字符数组填满时,检查组合的有效性,并将有效的组合添加到结果列表中。

源码实现

java 复制代码
class Solution {
    public List<String> generateParenthesis(int n) {
        // 创建一个列表来存储所有有效的括号组合
        List<String> combinations = new ArrayList<String>();
        // 调用递归函数生成所有可能的组合
        generateAll(new char[2 * n], 0, combinations);
        return combinations;
    }

    public void generateAll(char[] current, int pos, List<String> result) {
        // 如果当前位置到达数组末尾
        if (pos == current.length) {
            // 检查当前组合是否有效
            if (valid(current)) {
                // 如果有效,添加到结果列表
                result.add(new String(current));
            }
        } else {
            // 在当前位置放入左括号
            current[pos] = '(';
            generateAll(current, pos + 1, result); // 递归生成下一位置的组合
            
            // 在当前位置放入右括号
            current[pos] = ')';
            generateAll(current, pos + 1, result); // 递归生成下一位置的组合
        }
    }

    public boolean valid(char[] current) {
        int balance = 0; // 用于跟踪括号的平衡情况
        for (char c : current) {
            if (c == '(') {
                ++balance; // 左括号增加平衡
            } else {
                --balance; // 右括号减少平衡
            }
            // 如果平衡小于零,说明右括号多于左括号,组合无效
            if (balance < 0) {
                return false;
            }
        }
        // 只有当平衡为零时,才说明所有括号有效
        return balance == 0;
    }
}

复杂度评估

  • 时间复杂度:

    • 最坏情况下,算法会生成 O(2^(2n)) 种组合,这是由于每个位置都有两种选择(( 或 )),且组合的长度为 2n。
    • 然而,实际上有效的组合数量是 Catalan 数 C(n) = (2n)! / ((n+1)! * n!),因此实际生成的组合数会远少于 O(2^(2n))。
  • 空间复杂度:

    • 使用的空间主要是 result 列表和 current 数组。current 数组的长度为 2n,而 result 列表存储所有有效组合,最多为 O(C(n))。
    • 总体空间复杂度为 O(n)(用于存储 current 数组)加上 O(C(n))(存储有效组合),所以可以认为是 O(C(n))
相关推荐
小羊没烦恼!3 天前
微服务化的基石——持续集成
java·大数据·word·powerpoint·.net
倒头就睡的小比特3 天前
算法竞赛C++常用的STL
c++·算法
俊昭喜喜里3 天前
java中的继承和多态的区别
java
小羊没烦恼!3 天前
初探性能优化——2个月到4小时的性能提升
java·开发语言·windows·算法·c#
譕痕3 天前
JSONObject与JSONArray封装数据格式区别
java·json
胡写代码3 天前
别再前后端各写一套表单校验了
java·后端
小鱼能吃糖3 天前
缺陷修复总览 · mall电商项目:5类缺陷,1个病根,4个业务域
java·电商
此时不提桶,更待何时3 天前
01-06-A-JVM排查实战详解
java·jvm
猎头南楼3 天前
知识社区推荐系统实践:新用户冷启动与长短期兴趣建模的挑战 资深推荐算法工程师
人工智能·深度学习·算法·机器学习
vipxieliang3 天前
ValidX 在 DDD 领域驱动设计中的实践
java·spring boot