Here's a class I made:
public class ItemTree
{
public Int32 id { get; set; }
[JsonProperty(NullValueHandling = NullValueHandling.Ignore)]
public String text { get; set; }
[JsonProperty(NullValueHandling = NullValueHandling.Ignore)]
public List<ItemTree> item { get; set; }
public int parentId { get; set; }
}
And here's how I use it:
var tree = new ItemTree();
tree.id = 0;
tree.text = "sometext";
tree.item = new List<ItemTree>();
foreach (...)
{
if (tree.item.Count == 0)
{
tree.item.Add(new ItemTree
{
id = my_id,
text = my_name,
item = new List<ItemTree>(),
parentId = my_par
});
}
else
{
tree.item.Where(x => x.id == my_par)
.Select(x => x.item)
.First()
.Add(new ItemTree
{
id = my_id,
text = my_name,
item = new List<ItemTree>(),
parentId = my_par
});
}
}
And it crashes in the line with the Where clause. the reason it crashes is this: the tree has one item who has a list of items, and my query only checks the first item of the tree, not his children.
How to search in the whole depth of the tree and add an item there?
This might help:
With usage like:
This will start recursive selection (deep traversal), where you can use other LinQ features, like
.Where()
.Solution of @AgentFire from 2013-06-13 at 12:14 must extended to
to get the inner items into your result list.
Thanks @AgentFire for this nice idea.
It might be convenient to flatten your tree structure into a list. Some logic will be easier to express if you just have an
IEnumerable<ItemTree>
that contains all the nodes of your tree. You're not losing any information, since you still have the parent ID on every node.This is a naturally recursive problem. Using a recursive lambda, try something like:
Note that when you make a recursive
Func
like this, you must declare theFunc
separately first, and set it to null.You could also flatten the list using an iterator-block method:
Either way, once the tree is flattened you can do simple Linq queries over the flattened list to find nodes:
Then, in order to add to the tree, you can do:
Where
flattenedTree
was generated using one of our two flattening strategies.I also want to note that
item
is not a great name for a property that is a list. Such properties are most often pluralized (items
). Also, properties are usually capitalized (Items
).You are using
First()
instead ofFirstOrDefault()
. You should do something like the following instead.You will need to recurse the tree somehow. One solution is to make an iterator for the
ItemTree
object, something like:Now locating the parent is trivial, something like