[路飞]_leetcode_95. 不同的二叉搜索树 II

96 阅读1分钟

给你一个整数 n ,请你生成并返回所有由 n 个节点组成且节点值从 1 到 n 互不相同的不同 二叉搜索树 。可以按 任意顺序 返回答案。

示例 1:

    1      1        2        3    3
     \      \      / \      /    /
      3      2    1   3    2     1
      /       \           /        \
     2         3         1          2
输入:n = 3
输出:[[1,null,2,null,3],[1,null,3,2],[2,1,3],[3,1,null,null,2],[3,2,null,1]]

示例 2:

输入:n = 1
输出:[[1]]

解题思路

这一题我们需要遍历每一个值,使得每一个值为根节点时,它的左右子树的不同情况组成新的树。

假设 1 - 43 为根节点
     3
    /  \
   2    4
  /
 1
      3
    /  \
   1    4
    \
     2
左子树的取值范围为 [1, 2]
接下来就以 1 为根节点的树
    1
     \
      22 为根节点的树
    2
  /
1
右子树的取值范围为 [4]

然后将 2 种左子树和 1 种右子树与根节点 3 拼接成2种情况的树。

代码

var dfs = function(l, r) {
    let ans = []
    if (l > r) {
        ans.push(null);
        return ans;
    }       
    for (let i = l; i <= r; i++) { // [1, 2] 为例 2 为根节点
        // i 为当前树的根节点
        // 那么左边的树就是的取值范围就是 [l, i - 1]
        let leftNodes = dfs(l, i - 1); // dfs(1, 1) {1, null, null}
        // 右边的树就是的取值范围就是 [i + 1, r]
        let rightNodes = dfs(i + 1, r) // dfs(3, 2) null
        // 左右子树的排列组合
        for (let leftN of leftNodes) {
            for (let rightN of rightNodes) {
                let t = new TreeNode(i, leftN, rightN) // TreeNode(2, 1, null)
                ans.push(t)
            }
        }
    }
    return ans
}
var generateTrees = function(n) {
    let ans = []
    if (n == 0) return ans
    return dfs(1, n)
};