题目描述
输入一棵二叉搜索树,将该二叉搜索树转换成一个排序的双向链表。要求不能创建任何新的结点,只能调整树中结点指针的指向。
思路一:(较麻烦)
1、当前结点有左子树,则当前结点连接到左子树递归产生的双项链表的最后,返回本节点;
2、当前结点有右子树,则当前结点连接到右子树递归产生的双项链表的最前,返回本节点;
3、叶子结点直接返回本节点;
注意:由于都是返回的本节点,所以需要寻找子链表最前最后的结点,最后返回时也需要寻找;
代码:
TreeNode* ConvertNode(TreeNode* pRootOfTree){
if(pRootOfTree == NULL)
return NULL;
TreeNode* left_Tree;
TreeNode* right_Tree;
if(pRootOfTree->left){
left_Tree = ConvertNode(pRootOfTree->left);
while(left_Tree->right){
left_Tree = left_Tree->right;
}
left_Tree->right = pRootOfTree;
pRootOfTree->left = left_Tree;
}
if(pRootOfTree->right){
right_Tree = ConvertNode(pRootOfTree->right);
while(right_Tree->left){
right_Tree = right_Tree->left;
}
right_Tree->left = pRootOfTree;
pRootOfTree->right = right_Tree;
}
return pRootOfTree;
}
public:
TreeNode* Convert(TreeNode* pRootOfTree)
{
if(pRootOfTree == NULL)
return NULL;
TreeNode* node = ConvertNode(pRootOfTree);
while(node->left){
node = node->left;
}
return node;
}
思路二:
先中序遍历存储各个节点,然后在修改各个节点的指针关系;
代码:
TreeNode* Convert(TreeNode* pRootOfTree)
{
// 基本条件判断
if(pRootOfTree == NULL) {
return NULL;
}
// 中序遍历,存储节点
vector<TreeNode*> inOrder;
traverseInorder(pRootOfTree, inOrder);
// 修改指针关系
for(int i=0; i<inOrder.size()-1; i++) {
inOrder[i]->right = inOrder[i+1];
}
for(int i=inOrder.size()-1; i>0; i--) {
inOrder[i]->left = inOrder[i-1];
}
return inOrder[0];
}
void traverseInorder(TreeNode* pRootOfTree, vector<TreeNode*>& inOrder)
{
if(pRootOfTree == NULL) {
return;
}
traverseInorder(pRootOfTree->left, inOrder);
inOrder.push_back(pRootOfTree);
traverseInorder(pRootOfTree->right, inOrder);
}