0

I want to flatten a hierarchy of objects with an open Generic T.

This link Recursive List Flattening

shows how to do that taking a passed IEnumerable. But I want to flatten a passed object T and

its property Children in a generic and recursively way.

U1.Children(U2,U3,U4)
U2.Children(U9,U10)
U3.Children(U11,U12)
U4.Children(U20,U30)

I pass to the method U1(selected node) and I want to get this flat list:

U1,U2,U3,U4,U9,U10,U11,U12,U20,U30

Is that possible somehow in a generic way?

Community
  • 1
  • 1
Pascal
  • 12,265
  • 25
  • 103
  • 195

2 Answers2

2

You could define a recursive extension method that accepts a function for retrieving children:

public static IEnumerable<T> Flatten<T>(this T root, Func<T, IEnumerable<T>> getChildren)
{
    IEnumerable<T> rootSingleton = new T[] { root };
    IEnumerable<T> children = getChildren(root);
    IEnumerable<T> descendants = children.SelectMany(child => Flatten(child, getChildren));
    return rootSingleton.Concat(descendants);
}

Then, you could consume it like so:

var flat = u1.Flatten(u => u.Children);
Douglas
  • 53,759
  • 13
  • 140
  • 188
0

if your hierarcy is only one level depth you might use select many with union

public IEnumerable<T> Flattern<T>(IEnumerable<T> input) where T : ISomeinterface {
    return input.SelectMany(t=> t.Children).Union(input)
}

Well this code will not compile uness you'll constraint it with some base class or interface that has a Children property. The compiler must know that the object has that propertyl

Oybek
  • 7,016
  • 5
  • 29
  • 49