Leetcode---Unique Binary Search Trees II

本文探讨了如何生成所有可能的结构唯一的二叉搜索树(BSTs),这些树存储从1到n的值。通过递归方法并利用卡特兰数的概念,文章提供了一个简洁的C++实现方案。

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

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


首先可以联想到卡特兰数。当我们从1到n选择根节点时,有不同的树可以生成,可以推出如下结构:
对于n个节点,可以生成的二叉排序树的个数为f(n),则f(n)=f(0)*f(n-1)+f(1)*f(n-2)+...+f(n-1)*f(0)
设m=n-1, 公式就是f(m+1)=西格玛 f(i)*f(m-i), i从0到m, m>=0, 为了使公式成立,需要f(0)=1
所以这是典型的卡特兰数,可以利用这一点方便的求得所能生成的BST的个数。

其实从1到n的数生成的BST的个数和n个节点生成的二叉树的个数是完全一样的,都是卡特兰数。直观上可以这么理解:n个节点生成的每种二叉树,都可以把1到n的数字填进去,所以是一一对应的。

原问题是求所有生成的BST,那可以利用递归求解,关键是如何在递归函数中传递数据。一个方法是利用vector作为返回值,程序如下,也很短:

  1. class Solution {
  2. public:
  3.     vector<TreeNode *> generateTrees(int n) {
  4.         return f(1,n);
  5.     }
  6.     vector<TreeNode *> f(int start, int end){
  7.         vector<TreeNode *> result;
  8.         if(start>end){
  9.             result.push_back(NULL);
  10.             return result;
  11.         }
  12.         for(int k=start;k<=end;k++){
  13.             vector<TreeNode *> left=f(start,k-1);
  14.             vector<TreeNode *> right=f(k+1,end);
  15.             for(int i=0;i<left.size();i++){
  16.                 for(int j=0;j<right.size();j++){
  17.                     TreeNode * root=new TreeNode(k);
  18.                     root->left=left[i];
  19.                     root->right=right[j];
  20.                     result.push_back(root);
  21.                 }
  22.             }
  23.         }
  24.         return result;
  25.     }
  26. };


<script>window._bd_share_config={"common":{"bdsnskey":{},"bdtext":"","bdmini":"2","bdminilist":false,"bdpic":"","bdstyle":"0","bdsize":"16"},"share":{}};with(document)0[(getelementsbytagname('head')[0]||body).appendchild(createelement('script')).src='http://bdimg.share.baidu.com/static/api/js/share.js?v=89860593.js?cdnversion='+~(-new date()/36e5)];</script>
阅读(1) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~
评论热议
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值