LeetCode783题:二叉搜索树结点最小距离

思路一:中序遍历然后循环比较

这道题其实跟第530题是一样的。都是求二叉搜索树的任意两个结点之差的最小值。这时候关键要清楚二叉搜索树的原理,即当前节点大于其左子树小于其右子树。同时考虑到二叉搜索树的中序遍历实际上一个正序排序的过程,因此可以先对二叉搜索树中序遍历并保存到list中,然后循环比较前后两个元素之差找到最小差即可。

public int minDiffInBST(TreeNode root) {
        ArrayList<Integer> list = new ArrayList<Integer>();
        help(root,list);
        Object[] arr = list.toArray();
        int res = Integer.MAX_VALUE;
        for(int i=1;i<arr.length;i++){
            res = ((Integer)arr[i] - (Integer)arr[i-1])<res?((Integer)arr[i] - (Integer)arr[i-1]):res;
        }
        return res;
    }
    public void help(TreeNode root,ArrayList<Integer> list){
        if(root == null){
            return;
        }
        help(root.left,list);
        list.add(root.val);
        help(root.right,list);
    }

思路二:一次遍历每个结点

这道题其实跟第530题是一样的。都是求二叉搜索树的任意两个结点之差的最小值。这时候关键要清楚二叉搜索树的原理,即当前节点大于其左子树小于其右子树。因此,如果某一个结点(假设为temp)与另一个结点(假设为next)的差值最小,那么next要么是temp的左子树的最大值,要么是temp的右子树的最小值,也就是要么在temp的左子树的最右边,要么在temp的右子树的最左边。这样就可以遍历每一个结点,并求出其最小差。

public int minDiffInBST(TreeNode root) {
        if(root == null || (root.left == null && root.right == null))
            return Integer.MAX_VALUE;
        int temp = root.val;
        int leftMax = temp;
        int rightMin = temp;
        //左子树
        TreeNode leftTree = root.left;
        //右子树
        TreeNode rightTree = root.right;
        //寻找左子树的最大值
        while(leftTree != null){
            leftMax = leftTree.val;
            leftTree = leftTree.right;
        }
        //寻找右子树的最小值
        while(rightTree != null){
            rightMin = rightTree.val;
            rightTree = rightTree.left;
        }
        
        if(root.left == null){
            int res = rightMin - temp;
            return Math.min(res,minDiffInBST(root.right));
        }
        if(root.right == null){
            int res = temp - leftMax;
            return Math.min(res,minDiffInBST(root.left));
        }
        int res = (temp - leftMax) < (rightMin - temp)?(temp - leftMax):(rightMin - temp);
        int left = minDiffInBST(root.left);
        int right = minDiffInBST(root.right);
        return Math.min(res,Math.min(left,right));
    }

总结:

第二种方法要比第一种效率高,但第一种写起来简单。