题目:
求第n棵二叉树
思路:用卡特兰数确定一共有几个节点,然后递归输出
代码:
#pragma comment(linker, "/STACK:1024000000,1024000000")
#include<iostream>
#include<algorithm>
#include<ctime>
#include<cstdio>
#include<cmath>
#include<cstring>
#include<string>
#include<vector>
#include<map>
#include<set>
#include<queue>
#include<stack>
#include<list>
#include<numeric>
using namespace std;
#define LL long long
#define ULL unsigned long long
#define INF 0x3f3f3f3f3f3f3f3f
#define mm(a,b) memset(a,b,sizeof(a))
#define PP puts("*********************");
template<class T> T f_abs(T a){ return a > 0 ? a : -a; }
template<class T> T gcd(T a, T b){ return b ? gcd(b, a%b) : a; }
template<class T> T lcm(T a,T b){return a/gcd(a,b)*b;}
// 0x3f3f3f3f3f3f3f3f
LL h[30];
void Init(){
h[0]=h[1]=1;
for(int i=2;i<=25;i++)
h[i]=h[i-1]*(4*i-2)/(i+1);
}
void dfs(int k,int pos){
if(k==1){
printf("X");
return;
}
if(pos<=h[k-1]){//只有右子树
printf("X");
printf("(");
dfs(k-1,pos);
printf(")");
return;
}
else if(pos>h[k]-h[k-1]){//只有左子树
printf("(");
dfs(k-1,pos-(h[k]-h[k-1]));
printf(")");
printf("X");
}
else{
int t=k-1,m;
for(int i=t;i>=0;i--){
if(pos>h[t-i]*h[i])
pos-=h[t-i]*h[i];
else{
m=i;
break;
}
}
printf("(");
dfs(t-m,pos/h[m]+(pos%h[m]!=0));
printf(")");
printf("X");
printf("(");
dfs(m,(pos%h[m]==0)?h[m]:(pos%h[m]));
printf(")");
}
}
int main(){
int m,n;
Init();
while(~scanf("%d",&n)){
if(!n)
break;
for(int i=1;;i++){
if(n>h[i]){
n-=h[i];
}
else{
m=i;
break;
}
}
dfs(m,n);
printf("\n");
}
return 0;
}