[Leetcode] Unique Binary Search Trees II

Unique Binary Search Trees II 题解

原创文章,拒绝转载

题目来源:https://leetcode.com/problems/unique-binary-search-trees-ii/description/


Description

Given an integer n, generate all structurally unique BST's (binary search trees) that store values 1...n.

Example

For example,
Given n = 3, your program should return all 5 unique BST's shown below.

   1         3     3      2      1
    \       /     /      / \      \
     3     2     1      1   3      2
    /     /       \                 \
   2     1         2                 3

Solution


class Solution {
private:
    void delTree(TreeNode *root) {
        if (root == NULL)
            return;
        queue<TreeNode*> q;
        q.push(root);
        while (!q.empty()) {
            TreeNode* node = q.front();
            q.pop();
            if (node -> left != NULL)
                q.push(node -> left);
            if (node -> right != NULL)
                q.push(node -> right);
            delete node;
        }
    }

    TreeNode* copyTree(TreeNode* root, int offset) {
        if (root == NULL)
            return NULL;
        TreeNode* newRoot = new TreeNode(root -> val + offset);
        queue<TreeNode*> q1, q2;
        q1.push(newRoot);
        q2.push(root);
        TreeNode *node1, *node2;
        while (!q1.empty() && !q2.empty()) {
            node1= q1.front();
            q1.pop();
            node2 = q2.front();
            q2.pop();
            if (node2 -> left != NULL) {
                node1 -> left = new TreeNode(node2 -> left -> val + offset);
                q1.push(node1 -> left);
                q2.push(node2 -> left);
            }
            if (node2 -> right != NULL) {
                node1 -> right = new TreeNode(node2 -> right -> val + offset);
                q1.push(node1 -> right);
                q2.push(node2 -> right);
            }
        }
        return newRoot;
    }

public:
    inline void delTrees(vector<TreeNode*>& trees) {
        for (int i = 0; i < trees.size(); i++) {
            delTree(trees[i]);
        }
        trees.clear();
    }
    vector<TreeNode*> generateTrees(int n) {
        vector<vector<TreeNode*> > results(n + 1);
        if (n == 0) {
            return results[0];
        }
        results[0].push_back(NULL);
        int i, len;
        for (len = 1; len <= n; len++) {
            for (i = 1; i <= len; i++) {
                for (auto& lchild: results[i - 1]) {
                    for (auto& rchild: results[len - i]) {
                        TreeNode* parent = new TreeNode(i);
                        parent -> left = copyTree(lchild, 0);
                        parent -> right = copyTree(rchild, i);
                        results[len].push_back(parent);
                    }
                }
            }
        }

        for (int i = 0; i < n; i++) {
            delTrees(results[i]);
        }

        return results[n];
    }
};


解题描述

这道题可以说是第一个版本的拓展,不过需要求出所有不同形态的BST的实际结构。这里考虑使用DP来解决:

  • 对一定的长度的数据,其能得到的BST的类型数是固定的
  • 如果是数据不同,由于数据是连续的,相同数据量的BST子树拷贝时只需要对每个节点加上数据偏移量offset
  • 从0~n,求出所有长度的数据对应的BST,每次求的时候只需要使用前面求得的BST进行子树拷贝、偏移量设置还有子树拼接,也就是DP使用的地方
posted @ 2018-01-23 22:15  言何午  阅读(110)  评论(0编辑  收藏  举报