我怎样才能做到这一点?不

时间:2013-07-29 21:50:59

标签: iphone

有没有办法

我知道第一眼看上去没有意义,但我能以某种方式做到吗?

P

2 个答案:

答案 0 :(得分:2)

对于一般树的InOrder遍历并没有多大意义。由于没有“Order”,您应该访问当前节点。 InOrder只对二叉树有意义。

要使InOrder对一般树有意义,您必须定义当前节点应该访问的顺序。由于唯一有意义的两个选择是首先访问当前节点(这是预订)或者最后一次(这是后期订购)。因此,一般树的InOrder并没有多大意义。

当然,如果您的常规树具有特定结构,则InOrder可以有意义。如果你总是让前3个孩子离开而其他所有孩子都是对的,那么你的算法就像这样...

inorder(node)
  if node == null then return
  inorder(node.first)
  inorder(node.second)
  inorder(node.third)
  visit(node)
  foreach (remainingNode in RemainingNodes)
     inorder(remainingNode)

通用代码作为扩展方法......

    static public IEnumerable<Node<T>> InOrder<T>(this Node<T> thisNode)
    {
        var list = new List<Node<T>>();
        IEnumerable<Node<T>> leftNodes;
        IEnumerable<Node<T>> rightNodes;
        if (thisNode.Children == null)
        {
            leftNodes = new List<Node<T>>();
            rightNodes = new List<Node<T>>();
        }
        else
        {
            leftNodes = thisNode.Children.Take((int)Math.Ceiling(thisNode.Children.Count() / 2.0)).ToList();
            rightNodes = thisNode.Children.Skip(leftNodes.Count()).ToList();
        }
        if (leftNodes.Any())
        {
            foreach (var child in leftNodes)
            {
                list.AddRange(child.InOrder());
            }
        }
        list.Add(thisNode);
        if (rightNodes.Any())
        {
            foreach (var child in rightNodes)
            {
                list.AddRange(child.InOrder());
            }
        }
        return list;
    }

答案 1 :(得分:1)

按顺序遍历要求按顺序访问节点

  1. 对于非二叉树,这种行为没有意义,因为没有左或右专用节点。正如凯文所说,只有真的才有意义执行订单前或订单后的遍历;但是,如果要执行In-Order-esque遍历,则可以访问一半的子节点,此节点,然后访问另一半。但这并非真正符合有序遍历的精神。

    例如,假设您的节点有5个孩子。这将使顺序遍历:

    1. child 1
    2. child 2
    3. child 3
    4. child 4
    5. child 5
    6. (仅仅是为了争论。从技术上讲,孩子3,这可以交换,但会出现同样的问题)

      如果删除子5,则顺序遍历为:

      1. child 1
      2. child 2
      3. child 3
      4. child 4
      5. 并且固有顺序已经改变。

        但是,如果你要维护两个孩子列表:一个是你的leftChildren而另一个是rightChildren,那么有序遍历会像在二进制中那样有意义。树。但是,如何选择哪个孩子在哪个列表中完全是另一个问题。

        编辑:既然看起来你想要继续这样做,你可以用这样的东西来做:

        public IEnumerable<Node<T>> InOrder()
        {
            if (Children != null)
            {
                for (int i = 0; i < Children.length; i++)
                {
                    if (i == Children.length / 2)
                    {
                        yield return this;
                    }
        
                    foreach (var node in Children[i].InOrder())
                    {
                        yield return node;
                    }
                }
            }
        }