lotus

贵有恒何必三更眠五更起 最无益只怕一日曝十日寒

  博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

1. 题目

 

 

读题

https://leetcode.cn/problems/generate-parentheses/

这道题的题目描述是这样的:

给定一个整数n,表示括号对的数量,写一个函数来生成所有可能的有效括号组合。¹

有效括号组合的意思是,每个左括号都有一个对应的右括号,并且括号之间的嵌套关系是正确的。

例如,n = 3时,有以下五种有效括号组合:

((()))
(()())
(())()
()(())
()()()

考查点

这道题的考查点主要有以下几个:

1. **深度优先搜索(dfs)**的思想和实现,如何用递归或栈来遍历所有可能的括号组合。
2. **剪枝**的技巧,如何在生成括号的过程中,判断当前括号是否有效,避免无效的搜索。
3. **字符串**的操作,如何用字符串拼接或StringBuilder来构造括号组合。
4. **回溯**的方法,如何在递归返回时,恢复之前的状态,继续搜索其他分支。

这道题是一道经典的dfs题目,也是一道常见的面试题。掌握了这道题的解法,可以帮助你理解和解决其他类似的问题,比如生成所有可能的IP地址、生成所有可能的电话号码字母组合等。

2. 解法

思路

代码的思路。

首先,我们定义一个列表ans来存放结果,一个字符串cur来表示当前生成的括号组合,两个整数left和right来表示已经使用的左括号和右括号的数量,一个整数n来表示括号对的数量。

然后,我们调用dfs方法,传入ans, cur, left, right, n这五个参数。dfs方法的作用是递归地生成所有可能的括号组合,并把有效的组合加入到ans列表中。

在dfs方法中,我们首先判断当前字符串cur的长度是否等于2n,如果是,说明已经生成了一个有效的括号组合,因为每个括号对都有一个左括号和一个右括号,所以总共有2n个字符。这时候,我们把cur加入到ans列表中,并结束递归。

如果当前字符串cur的长度不等于2n,说明还可以继续添加括号。这时候,我们有两种选择,要么添加左括号,要么添加右括号。但是,并不是所有的选择都是有效的。我们需要满足以下两个条件:

  1. 左括号的数量不能超过n,否则就会出现多余的左括号。
  2. 右括号的数量不能超过左括号的数量,否则就会出现不匹配的右括号。

所以,我们只有在满足这两个条件的情况下,才能继续添加括号。具体地,如果左括号的数量left小于n,我们就可以递归地调用dfs方法,把左括号加入到当前字符串cur中,并把left加一。如果右括号的数量right小于左括号的数量left,我们就可以递归地调用dfs方法,把右括号加入到当前字符串cur中,并把right加一。

通过这样的递归过程,我们就可以遍历所有可能的括号组合,并把有效的组合加入到ans列表中。最后,我们返回ans列表作为结果。

 

剪枝是一种削减搜索空间的方法,它可以在搜索过程中,提前判断某些分支是否有必要继续搜索,如果没有必要,就把这些分支舍弃,从而减少无效的搜索次数。剪枝可以

具体实现

class Solution {
    public List<String> generateParenthesis(int n) {
        List<String> ans = new ArrayList<>(); // 存放结果的列表
        dfs(ans, "", 0, 0, n); // 调用dfs方法
        return ans; // 返回结果
    }

    public void dfs(List<String> ans, String cur, int left, int right, int n) {
        if (cur.length() == 2 * n) { // 如果当前字符串长度等于2n,说明已经生成了一个有效的括号组合
            ans.add(cur); // 把当前字符串加入结果列表
            return; // 结束递归
        }
        if (left < n) { // 如果左括号的数量小于n,可以继续添加左括号
            dfs(ans, cur + "(", left + 1, right, n); // 递归调用,把左括号加入当前字符串,左括号数量加一
        }
        if (right < left) { // 如果右括号的数量小于左括号的数量,可以继续添加右括号
            dfs(ans, cur + ")", left, right + 1, n); // 递归调用,把右括号加入当前字符串,右括号数量加一
        }
    }
}

  

 

3. 总结

posted on 2023-04-29 23:17  白露~  阅读(14)  评论(0编辑  收藏  举报