使用递归Func委托遍历Tree结构时的Stackoverflow

时间:2014-04-04 07:05:43

标签: c# tree treeview func

我试图遍历如下定义的树状结构

public class TreeItem
{
    string _Name;
    public string Name
    {
        get { return _Name; }
        set { _Name = value; }
    }

    bool _IsChecked;
    public bool IsChecked
    {
        get { return _IsChecked; }
        set { _IsChecked = value; }
    }

    Visibility _CheckBoxVisibility;
    public Visibility CheckBoxVisibility
    {
        get { return _CheckBoxVisibility; }
        set { _CheckBoxVisibility = value; }
    }

    Visibility _ImageVisibility;
    public Visibility ImageVisibility
    {
        get { return _ImageVisibility; }
        set { _ImageVisibility = value; }
    }

    List<TreeItem> _Children;
    public List<TreeItem> Children
    {
        get { return _Children; }
        set { _Children = value; }
    }

    public TreeItem()
    {
        Children = new List<TreeItem>();
        IsChecked = true;
        CheckBoxVisibility = Visibility.Collapsed;
    }

    public TreeItem(TreeItem t)
    {
        Children = t.Children;
        Name = t.Name;
    }

    public void AddChild(TreeItem _Child)
    {
        Children.Add(_Child);
    }

}

Func委托声明

Func<TreeItem, TreeItem> Traverse = null;
Traverse = (t) => (t.Children.Count == 0) ? t : Traverse(t) ;

但是当我调用它时会给出一个stackoverflow expception,我知道它是由于再次传递给Travese导致无限循环引起的。我想要一个解决方案,通过它我可以将Children属性而不是整个类对象传递给Travese。

2 个答案:

答案 0 :(得分:1)

我认为会这样做:

Traverse = (t) => (t.Children.Count == 0) ? t : Traverse(t.Children[0]) ;

答案 1 :(得分:0)

Traverse = t => t.Children.ForEach(Traverse);

如果在根上使用,这将遍历整个树。但它没有任何回报价值。您可以检查的可能方式:

TraverseAndCheckIfAnyIsChecked = t => t.IsChecked || t.Children.Any(TraverseAndCheckIfAnyIsChecked);


TraverseAndCheckIfAllAreChecked = t => t.IsChecked && t.Children.All(TraverseAndCheckIfAallAreChecked);