把二元查找树转变成排序的双向链表(树)
题目:
输入一棵二元查找树,将该二元查找树转换成一个排序的双向链表。
要求不能创建任何新的结点,只调整指针的指向。
10
/ \
6 14
/ \ / \
4 8 12 16
转换成双向链表
4=6=8=10=12=14=16。
题目:
输入一棵二元查找树,将该二元查找树转换成一个排序的双向链表。
要求不能创建任何新的结点,只调整指针的指向。
10
/ \
6 14
/ \ / \
4 8 12 16
转换成双向链表
4=6=8=10=12=14=16。
思路:中序遍历二叉查找树,因此结点按从小到大顺序访问,假设之前访问过的结点已经调整为一个双向链表,那么只需要将当前结点连接至双向链表的最后一个结点即可,访问完后,双向链表也就调整完了。
完整代码:
#include<stdio.h>
#include<malloc.h>
#include<assert.h>
//结点结构
typedef struct _Node{
struct _Node *left;
struct _Node *right;
int elem;
}DuLNode;
DuLNode *pHead=NULL;
DuLNode *pRear=NULL;
void Tree_to_DuLinkList(DuLNode * );
//插入节点,构造二叉树
void addTreeNode(DuLNode *&root,int e)
{
if(root==NULL)
{
root=(DuLNode *)malloc(sizeof(DuLNode));
assert(root);
root->elem = e;
root->left = NULL;
root->right = NULL;
}
else if(root->elem > e)
{
addTreeNode(root->left,e);
}
else
{
addTreeNode(root->right,e);
}
}
//中序遍历二叉树,同时调整结点指针
void InOrderTrv(DuLNode *root)
{
if(NULL==root)
return;
InOrderTrv(root->left);
Tree_to_DuLinkList(root); //调整结点指针
InOrderTrv(root->right);
}
//调整结点指针
void Tree_to_DuLinkList(DuLNode *root)
{
root->left = pRear; //root->left指向已有双向链表的尾结点pRear
if(NULL!=pRear) //pRear!=NULL说明双向链表已经生成,
{
pRear->right = root; //已有双向链表的尾结点pRear->right指向root
}
else
{
pHead = root; //pRear==NULL说明还未生成双向链表,则此时的root节点作为头结点pHead
}
pRear = root; //先加入的root结点作尾结点
printf("%d\n",root->elem);
}
int main()
{
DuLNode *root=NULL;
addTreeNode(root,10);
addTreeNode(root,6);
addTreeNode(root,14);
addTreeNode(root,4);
addTreeNode(root,8);
addTreeNode(root,12);
addTreeNode(root,16);
InOrderTrv(root);
return 0;
}