生成一个节点小于100的二叉搜索树。生成后把二叉树变成图存储在Map.txt文件中。
如果想要有序数组的二叉搜索树,则直接把随机生成的数组list1进行排序即可。
代码:
#include<bits/stdc++.h>
using namespace std;
const int N = 100;
//定义结点结构体
struct Node{
int val;
Node *left;
Node *right;
int tem1,tem2;
};
Node *Tree;
Node tree[N];
int n,list1[N];
int len;
void array_to_binary_search_tree();
Node *Insert(Node *T,int x);
Node *creatT();
void showmap(Node *T);
void getWidth(Node *Tree, int depth, int shift, char map[N][N*2]);
int main()
{
cin>>n;
for (int i=0;i<n;i++)
{
//随机生成一个数字介于(0~1000)之间
list1[i] = rand() % 999 +1;
}
list1[n] = 0;
array_to_binary_search_tree();
return 0;
}
//将数组转换为二叉搜索树。
void array_to_binary_search_tree()
{
len=0;
for(int i=0;i<N;i++)
{
if(list1[i]==0) break;
else
{
Tree=Insert(Tree,list1[i]);
}
}
showmap(Tree);
}
//节点插入函数
Node *Insert(Node *T,int x)
{
if(!T) //节点处为空,创建一个结点
{
T = creatT();
T->val = x; //对结点赋值
return T; //返回根结点指针
}//if
if (x < T->val) //x的权值小于根节点,递归插入左边
{
T->left = Insert(T->left,x);
}//else if
if (x > T->val) //x的权值大于根节点,递归插入右边
{
T->right = Insert(T->right,x);
}//else if
return T;
}
//创建一个节点
Node *creatT()
{
tree[len].left=NULL;
tree[len].right=NULL;
return &tree[len++];
}
//把二叉树展示在Map.txt中
void showmap(Node *T)
{
char graph[N][N*2];
memset(graph,' ',sizeof graph);
ofstream r;
r.open("Map.txt");
if(!T)
{
r<<"空树";
r.close();
return ;
}
getWidth(T,0,0,graph);
for (int i=0; i<N; i++)
{
int k=N*2-1;
while(k>=0 && graph[i][k]==' ')
k--;
for(int j=0; j<=k; j++)
{
r<<graph[i][j];
}
r<<"\n";
}
}
//得到每一行的宽度
void getWidth(Node *Tree, int depth, int shift, char map[N][N*2])
{
int i;
if (Tree->left != NULL)
{
getWidth(Tree->left, depth+1, shift, map);
Tree->tem1 = Tree->left->tem1 + Tree->left->tem2 + 1;
for (i=(Tree->left->tem1+shift)*2; i<shift*2; i=i+2)
{
map[depth*2+1][i]='-';
map[depth*2+1][i+1]='-';
}
}
else Tree->tem1 = 0;
if (Tree->right != NULL)
{
getWidth(Tree->right, depth+1, shift+Tree->tem1+1, map);
Tree->tem2 = Tree->right->tem1 + Tree->right->tem2 + 1;
}
else Tree->tem2 = 0;
for (i=shift*2; i<(Tree->tem1+shift)*2; i++)
map[depth*2][i]=' ';
map[depth*2][(Tree->tem1+shift)*2]=(char)(Tree->val / 1000 +48);
map[depth*2][(Tree->tem1+shift)*2+1]=(char)(Tree->val / 100 % 10 +48);
map[depth*2][(Tree->tem1+shift)*2+2]=(char)(Tree->val / 10 % 10 +48);
map[depth*2][(Tree->tem1+shift)*2+3]=(char)(Tree->val %10 +48);
if (Tree->val<1000)
{
map[depth*2][(Tree->tem1+shift)*2]=' ';
if (Tree->val <100)
{
map[depth*2][(Tree->tem1+shift)*2+1]=map[depth*2][(Tree->tem1+shift)*2+2];
map[depth*2][(Tree->tem1+shift)*2+2]=map[depth*2][(Tree->tem1+shift)*2+3];
map[depth*2][(Tree->tem1+shift)*2+3]=' ';
if (Tree->val < 10)
map[depth*2][(Tree->tem1+shift)*2+1]=' ';
}
}
if (Tree->left != NULL)
{
map[depth*2+1][(Tree->left->tem1+shift)*2+1]=(char)0xa9;
map[depth*2+1][(Tree->left->tem1+shift)*2+2]=(char)0xb0;
map[depth*2+1][(Tree->tem1+shift)*2+1]=(char)0xa9;
map[depth*2+1][(Tree->tem1+shift)*2+2]=(char)0xbc;
for (i=(Tree->left->tem1+shift)*2+3; i<(Tree->tem1+shift)*2; i=i+2)
{
map[depth*2+1][i]=(char)0xa9;
map[depth*2+1][i+1]=(char)0xa4;
}
}
if (Tree->right != NULL)
{
map[depth*2+1][(Tree->tem1+shift)*2+1]=(char)0xa9;
map[depth*2+1][(Tree->tem1+shift)*2+2]=(char)0xb8;
map[depth*2+1][(Tree->tem1+Tree->right->tem1+shift)*2+3]=(char)0xa9;
map[depth*2+1][(Tree->tem1+Tree->right->tem1+shift)*2+4]=(char)0xb4;
for (i=(Tree->tem1+shift)*2+3; i<(Tree->tem1+Tree->right->tem1+shift)*2+2; i=i+2)
{
map[depth*2+1][i]=(char)0xa9;
map[depth*2+1][i+1]=(char)0xa4;
}
}
if (Tree->left != NULL && Tree->right != NULL)
{
map[depth*2+1][(Tree->tem1+shift)*2+1]=(char)0xa9;
map[depth*2+1][(Tree->tem1+shift)*2+2]=(char)0xd8;
}
}
我觉得参考linux里tree命令的作图法会好一点哦 >_<
这个建树还比较简单, 我觉得如何计算左右空间 在txt上正确的显示空间才是难的。
如果挑战下极限情况,数目太多 一屏显示不下,如何处理? 那就更难了
对的,txt建图的确挺难的……
大佬可以的!
就是我输了个250进去怎么还看见日语了😏
这个我的getwidth()函数还在调试中……
节点少一点的树还是没问题的,可能横线什么的位置或长度不太对……