代码随想录day23| 修剪二叉搜索树 将有序数组转换为二叉搜索树 把二叉搜索树转换为累加树

修剪二叉搜索树

分析:首先确定遍历顺序为中左右的前序遍历,对于中间节点,如果其值不在[low, high]的范围内,那么是需要修剪的节点,如果root.val < low,那么就需要一个大于root.val的节点来代替当前节点,所以需要向右遍历,并返回。同理,当root.val > high,向左遍历。最后遍历左右子树即可。

  • 将root移动到[L, R] 范围内,注意是左闭右闭区间
  • 剪枝左子树
  • 剪枝右子树
class Solution {
    public TreeNode trimBST(TreeNode root, int low, int high) {
        if (root == null) {
            return null;
        }
        if (root.val < low) {
            return trimBST(root.right, low, high);
        }
        if (root.val > high) {
            return trimBST(root.left, low, high);
        }
        // root在[low,high]范围内
        root.left = trimBST(root.left, low, high);
        root.right = trimBST(root.right, low, high);
        return root;
    }
}

将有序数组转换为二叉搜索树

  • 分析:对于有序数组,中间的mid节点一定是跟节点,因此每次遍历时,先处理mid节点,第二步需要递归处理由mid分割的左右节点,分别用root.left和root.right接收,最后返回根节点即可。

class Solution {
    public TreeNode sortedArrayToBST(int[] nums) {
        TreeNode root = traversal(nums, 0, nums.length - 1);
        return root;
    }

    // 左闭右闭区间[left, right]
    private TreeNode traversal(int[] nums, int left, int right) {
        if (left > right) return null;

        int mid = left + ((right - left) >> 1);
        TreeNode root = new TreeNode(nums[mid]);
        root.left = traversal(nums, left, mid - 1);
        root.right = traversal(nums, mid + 1, right);
        return root;
    }
}

把二叉搜索树转换为累加树

  • 分析:考虑到二叉树搜索树中序遍历是一个单调递增的数组,那么右中左遍历就是一个单调递减数组,既然题目含义是只加上大于等于当前节点的数值,那么设置一个pre记录前一个节点的值,然后采用右中左的遍历顺序遍历即可。

class Solution {
    int sum;
    public TreeNode convertBST(TreeNode root) {
        sum = 0;
        convertBST1(root);
        return root;
    }

    // 按右中左顺序遍历,累加即可
    public void convertBST1(TreeNode root) {
        if (root == null) {
            return;
        }
        convertBST1(root.right);
        sum += root.val;
        root.val = sum;
        convertBST1(root.left);
    }
}

 

posted @ 2023-03-09 21:36  绝云气负青天  阅读(16)  评论(0)    收藏  举报