UVA10821--Constructing BST(贪心+二分)

10 篇文章 0 订阅
1 篇文章 0 订阅
BST (Binary Search Tree) is an efficient data structure for searching. In a BST all the elements of the left sub-tree are smaller and those of right sub-tree are greater than the root. A typical example of BST is –

                           

Normally, we construct BST by successively inserting an element. In that case, the ordering of elements has great impact on the structure of the tree. Look at the following cases:

 

In this problem, you have to find the order of 1 to N integers such that the BST constructed by them has height of at most H. The height of a BST is defined by the following relation –

1.      BST having no node has height 0.

2.      Otherwise, it is equal to the maximum of the height of the left sub-tree and right sub-tree plus 1.

 

Again, several orderings can satisfy the criterion. In that case we prefer the sequence where smaller numbers come first. For example, for N=4,H=3 we want the sequence 1 3 2 4 rather than 2 1 4 3 or 3 2 1 4.

 

Input
Each test case starts with two positive integers N(1≤N≤10000) and H (1≤H≤30). Input is terminated by N=0, H=0. This case should not be processed. There can be at most 30 test cases.

 

Output

Output of each test case should consist of a line starting with “Case #: “where ‘#’ is the test case number. It should be followed by the sequence of N integers in the same line. There must not be any trailing space at the end of the line. If it is not possible to construct such tree then print “Impossible.” (without the quotes).

 

Sample Input                               Output for Sample Input

4 3

4 1

6 3

0 0

Case 1: 1 3 2 4

Case 2: Impossible.

Case 3: 3 1 2 5 4 6



题意:给出n和h,构建一个二叉树,使得高度至高为h且字典序最小。

思路:就是一个贪心的意识。如果能在左边放x个右边放y实现高度至高为h,绝对比左边放x+1个,右边放y-1个字典序更小。

#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
bool Judge(int num,int h)
{
	if((1 << h) - 1 >= num)	return 1;
	return 0;
}
void Print(int add,int n,int res)
{
	if(n == 0)	return;
	if(n == 1)	
	{
		printf(" %d",add+1);
		return;
	}
	int l = 0,r = n-1,ans = n-1;
	while(l <= r)
	{
		int mid = (l+r) >> 1;
		if(Judge(mid,res-1) && Judge(n-1-mid,res-1))
		{
			ans = mid;
			r = mid - 1;
		}
		else l = mid + 1;
	}
	printf(" %d",add+ans+1);
	Print(add,ans,res-1);
	Print(add+ans+1,n-1-ans,res-1);
}
int main()
{
	int n,h,cas = 0;
	while(scanf("%d%d",&n,&h)==2 && n|h)
	{
		cas++;
		printf("Case %d:",cas);
		if((1 << h) - 1 < n)
		{
			printf(" Impossible.\n");
			continue;
		}
		Print(0,n,h);
		puts("");	
	}
	return 0;
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值