输入一棵二叉搜索树,将该二叉搜索树转换成一个排序的双向链表。要求不能创建任何新的结点,只能调整树中结点指针的指向。
二叉搜索树的特点:
- 对于树上的任意节点,左子树节点小于根节点,右子树节点大于根节点。
- 二叉搜索树中序遍历可以得到一个有序的序列。
求解思路:通过中序遍历来转换
- 递归将左子树转换成双向链表;
- 将根节点尾插到左子树链表的末尾;
- 递归将右子树转成链表;
- 将根节点头插到右子树链表前面。
代码实现:
/**
public class TreeNode {
int val = 0;
TreeNode left = null;
TreeNode right = null;
public TreeNode(int val) {
this.val = val;
}
}
*/
public class Solution {
public TreeNode Convert(TreeNode pRootOfTree) {
if(pRootOfTree == null){
return null;
}
if(pRootOfTree.left == null && pRootOfTree.right == null){
return pRootOfTree;
}
//递归将左子树转成链表
TreeNode leftHead = Convert(pRootOfTree.left);
TreeNode leftTail = leftHead;
//将根节点尾插到leftHead链表中(需先找到尾节点的位置再尾插)
while(leftTail != null && leftTail.right != null){
leftTail = leftTail.right;
}
if(leftHead != null){
leftTail.right = pRootOfTree;
pRootOfTree.left = leftTail;
}
//递归将右子树转换成链表
TreeNode rightHead = Convert(pRootOfTree.right);
//将当前节点头插到右侧链表的前面
if(rightHead != null){
pRootOfTree.right = rightHead;
rightHead.left = pRootOfTree;
}
//返回最终链表的头节点
//若leftHead是空链表,应返回pRootOfTree
return leftHead != null ? leftHead : pRootOfTree;
}
}