检查二叉树是否为BST的函数始终返回true

时间:2014-05-07 11:57:49

标签: java algorithm binary-search-tree

我编写了一个递归程序,用于检查二叉树是否为BST。

我写了一个返回truefalse的基本案例,但我在递归案例中感到困惑。

这个程序进行递归调用,但它没有工作,虽然我感觉很好。

public class BinaryBSTChecker {
    public static boolean isBinaryBST(Node node) {
        if ( node != null) {
            Node leftNode = node.getLeftNode();
            Node rightNode = node.getRightNode();
            int value = node.getValue();

            isBinaryBST(leftNode) ;
            isBinaryBST(rightNode) ;

            boolean leftIsOk = isLeftOK(leftNode , value);
            boolean rightIsOk = isRightOK(rightNode, value);

            return (leftIsOk && rightIsOk);
        }
        return false;
    }

    private static boolean isLeftOK(Node leftNode, int value) {
        boolean leftOK = false;

        if (leftNode != null) {
            if (leftNode.getValue() < value) {
                leftOK =  true;
            }
        } else {
            leftOK = true;
        }
        return leftOK;
    }

    private static boolean isRightOK(Node rightNode, int value) {
        boolean rightOK = false;

        if (rightNode != null ) {
            if (rightNode.getValue() > value)  {
                rightOK = true;
            }
        } else {
            rightOK = true;
        }
        return rightOK;
    }
}

客户代码:

public class TestingClient {
    public static void main (String[] args) {
        Node node = getBSTTree() ;

        System.out.println("------Is Binary BST ?------>"
                           + BinaryBSTChecker.isBinaryBST(node));
    }

    public static Node getBSTTree() {
        Node node = new Node(9);
        Node leftNode = new Node(7);
        Node rightNode = new Node(11);
        Node leftNode2 = new Node(67);
        Node rightNode2 = new Node(8);
        Node leftNode3 = new Node(10);
        Node rightNode3 = new Node(12);

        node.setLeftNode(leftNode);
        node.setRightNode(rightNode);
        leftNode.setLeftNode(leftNode2);
        leftNode.setRightNode(rightNode2);
        rightNode.setLeftNode(leftNode3);
        rightNode.setRightNode(rightNode3);

        return node;
    }
}

上面的树不是BST 67 > 7

所以这应该返回false,但我得到true这个案例,事实上对于所有情况。

3 个答案:

答案 0 :(得分:1)

为什么在public static boolean isBinaryBST(Node node)结束时返回false?

在那里返回true,应该没问题。

编辑: 显然这是一个错误,但我没有好好看看代码。

这里还有一件事。 调用isLeftOK和isRightOk,但也在左边和右边。正确的节点,但也有调用

isBinaryBST(leftNode) ;
isBinaryBST(rightNode);

似乎忽略了这些结果,这是一个问题。

返回应该是这样的:

return (leftIsOk && rightIsOk && isBinaryBST(leftNode) && isBinaryBST(rightNode));

答案 1 :(得分:0)

添加空检查,否则它将进入无限循环

if(leftNode != null)
    isBinaryBST(leftNode) ;
if(rightNode != null)
    isBinaryBST(rightNode) ;

boolean leftIsOk = true;
boolean rightIsOk = true;
if(leftNode != null)
    leftIsOk = isLeftOK(leftNode , value); ;
if(rightNode != null)
    rightIsOk = isRightOK(rightNode, value);
return (leftIsOk && rightIsOk);

答案 2 :(得分:0)

你在递归调用中忽略了isBinaryBST的返回值,因此该函数只返回root的子节点是否正确。

但是你试图从根本上解决问题的方式是行不通的。

拿这棵树:

  5
 /
3
 \
  7

这不是有效的BST,如7 > 5

你无法通过只看直接的孩子来检查这一点。

推荐的方法是将minmax传递给您的函数,即签名将是:

boolean isBinaryBST(Node node, int min, int max)

简单地检查当前节点的值是否在两者之间(或节点为空)(不需要辅助函数),并对子节点进行适当的递归调用(并记住检查它们的返回值!)。一般的想法是:(伪代码)

return (current node is between min and max)
    && (left subtree is okay, i.e. recursive call with left child)
    && (right subtree is okay, i.e. recursive call with right child)

我会留下准确的细节给你解决。

在上面的示例中,当我们到达7min = 3max = 5时,我们会看到7 > max,并返回false