关于获取二叉树中节点数的问题

时间:2010-05-07 22:11:23

标签: data-structures

我已经编写了两个函数(伪代码),用于在给定树的根的情况下计算二进制树的节点数和树高。 最重要的是,二叉树表示为第一个chiled / next兄弟格式。

所以

struct TreeNode
{
  Object element;
  TreeNode *firstChild;
  TreeNode *nextSibling;
}

计算节点数:

public int countNode(TreeNode root)
{
     int count=0;
     while(root!=null)
     {
        root= root.firstChild;
        count++;
     }

      return count;
}

public int countHeight(TreeNode root)
{
     int height=0;
     while(root!=null)
     {
        root= root.nextSibling;
        height++;
     }

  return height;

}

这是我在算法书上看到的问题之一,我上面的解决方案似乎有一些问题,我也没有完全明白使用二元树的第一个孩子/右兄弟代表,你能不能伙计们给我一些想法和反馈,好吗? 干杯!

3 个答案:

答案 0 :(得分:1)

下一个兄弟和第一个孩子的使用可能是这样的:

A1 -- A2 -- A3
|     |    
|     B1 -- B2 -- B3
|           |
D1 -- D2    C1

图中的水平线代表nextSibling,垂直线代表firstChild链接。对于某些问题,这可能是自然可视化(但对于其他一些问题,您可能更喜欢通常的树有两个子节点 - 它们是等效的。)

你的伪代码似乎遗漏了一些东西,因为你并没有真正计算任何东西。我想你想在count++循环中分别height++ while

无论如何,要计算节点数,您需要添加子节点的数量以及同一级别(兄弟节点)上的节点数。对于相当小的树,这可以递归地完成:

public int countNode(TreeNode root) { 
  if (root == null) return 0;
  return 1 + countNodes(root.firstChild) 
           + countNodes(root.nextSibling);
}

对于较大的数据结构,您需要将“待处理”节点存储在内存堆栈中以避免堆栈溢出(原文如此!)

要计算高度,首先需要确定如何定义高度。它是您遵循firstChild链接(即A1 -> D1)或您想要树中最长路径(任何地方)(可能是A1 -> A2 -> B1 -> B2 -> C1)的路径。在第一种情况下,您的实施是正确的。在第二种情况下,您需要一个类似于计数节点的递归函数(而不是添加,您将选择更大的子树)。

答案 1 :(得分:0)

虽然字面上是正确的,但“第一个孩子”和“正确的兄弟姐妹”可能会有点令人困惑。如果你用“左孩子”和“右孩子”代替,我认为你能够更好地理解它。

答案 2 :(得分:0)

要理解递归,首先必须理解递归。

public int countNode(TreeNode root) 
{ 
     if (root==null) { 
        return 0;
     } else {
        return countNode(root.firstChild) + countNode(root.nextSibling) + 1;
     }
}

public int countHeight(TreeNode root) 
{ 
     if (root==null) { 
        return 0;
     } else {
        return max(countHeight(root.firstChild),
                   countHeight(root.nextSibling)) + 1;
     }
}

如果树为空,则它不包含节点且没有高度。

如果树不为null,那么它比一个较高的子树高一个节点,它包含两个子树的所有节点,加上包含两个子树的节点。

阅读Dave Touretzky关于LISP的书。戴夫用龙故事教授递归,龙实际上是一位很好的老师。