Click here to Skip to main content
15,888,286 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
See more:
My tree is like this:-
Science
        Biology
                Human
        Physics
        Chemistry

now i want to search if Human exists in the whole tree (without iteration [for,while,do while or foreach]). How to do so?

I tried
1)
bool isExists = treeView1.Nodes.ContainsKey("Human");

but the bool variable always returned false.
2)
TreeNode[] Tnarray = treeView1.Nodes.Find("Human", true);

but the TreeNode Array always returned blank.
Posted
Updated 20-Feb-14 18:06pm
v3
Comments
SVT02 21-Feb-14 1:43am    
I don't Know your actual problem...But I want to suggest you ,Take Arraylist For this & take the boolen function To check whether Human is present or not?
agent_kruger 21-Feb-14 1:49am    
nice idea sir, but just want to ask that while converting 1,00,000 records will it make the program little slow?
LLLLGGGG 21-Feb-14 14:24pm    
What about using LINQ? It might be useful, but I haven't got a clue how to use it in a tree... https://www.google.it/?gfe_rd=ctrl&ei=rqcHU5yQCOjW8geFoIG4BQ&gws_rd=cr#q=tree+and+LINQ
agent_kruger 22-Feb-14 3:49am    
can you explain what is LINQ a quick search gave me no idea what it is? and how and where can it be used?
LLLLGGGG 23-Feb-14 8:23am    
LINQ is something like SQL, but you can use it within C# collections... http://msdn.microsoft.com/en-us/library/bb397926.aspx


1 solution

The OP here expressed the goal of finding any TreeNode in a TreeView without recursion, or some form of iteration: that is impossible. What is possible is to minimize the computation involved in searching for TreeNodes by building a "flattened" list of the Nodes. That technique is illustrated here.

When you execute code like treeView1.Nodes.ContainsKey("node key"); you search only the specific TreeNodeCollection of either the TreeView, or a Node in the TreeView. The 'IndexOfKey method works in the same way.

Beginning with FrameWork 2.0, the 'Find operator was implemented: this is a method of the TreeNodeCollection Class that takes a string which is the Name/Key of a Node, and a second, boolean, parameter which, if true, will search recursively through all the sub-nodes.

So, to search the entire TreeView for a TreeNode with the Key "Node14," you can call: treeView1.Nodes.Find("Node14", true). When you perform such a search, you trigger the internal recursive iteration of the underlying data structure, the TreeNodeCollections, and TreeNodes, of the TreeView.

To create a "flattened" list of all TreeNodes, and update that list whenever a TreeNode is added, or deleted, to the Tree:
C#
// list of all TreeNodes
private List<TreeNode> flatNodeList = new List<TreeNode>();

// create the flattened node list using recursion
private void createFlatList(TreeNodeCollection theNodes)
{
    foreach (TreeNode theNode in theNodes)
    {
        flatNodeList.Add(theNode);

        if(theNode.Nodes.Count != 0) createFlatList(theNode.Nodes);
    }
}

// build the flattened list in the Form_Load EventHandler
private void Form1_Load(object sender, EventArgs e)
{
    createFlatList(treeView1.Nodes);
}
Once you have that List of all TreeNodes, you can search it, and use all the regular generic List operators; you can use Linq on it to do complex queries, and analysis, and select sub-sets of nodes based on conditions, etc.

That leaves the question of how you update the flat-list as the user adds, or deletes, nodes at run-time; obviously you don't want to re-build the entire list recursively every time a single node is added, or deleted !

One way to update is to define your own methods for add, and delete, TreeNodes:
C#
private void AddNode(TreeNodeCollection theNodes, string key)
{
    TreeNode newNode = new TreeNode(key);
    
    flatNodeList.Add(newNode);
    
    theNodes.Add(newNode);
}

private void DeleteNode(TreeNode theNode)
{
    if(! flatNodeList.Contains(theNode)) throw new KeyNotFoundException("Invalid Node in DeleteNode");
    
    flatNodeList.Remove(theNode);
    
    // are we removing a top-level (root) Node ?
    // if so, the Parent is 'null
    if (theNode.Level == 0)
    {
        theNode.TreeView.Nodes.Remove(theNode);
    }
    else
    {
        // removing a Node that has a Parent Node
        theNode.Parent.Nodes.Remove(theNode);
    }
}
You can take the principles demonstrated here and use them to add other methods that might update the flat list, like 'AddRange.

Note: not every application using the standard TreeView might benefit ... much ... from avoiding using the 'Find operator to search by the techniques shown here. However, there are many other possible uses for a flattened list of all the Nodes.

If I were using a TreeView with an extremely large number of TreeNodes, deeply nested, with frequent need to do searches, I would certainly use the techniques shown here.

In some real applications I have written, not only have I created a flattened list of TreeNodes, I've created a data structure of the form Dictionary<int,List<treenode>>> ... this is built dynamically in the same recursive way I build a flattened List of all the TreeNodes, and ends up containing a separate TreeNodeCollection for nodes at each level in the TreeView.

Other techniques you can use include sub-classing the WinForms TreeView, and over-riding the methods you need to modify to keep a flattened list updated.
 
Share this answer
 
v4
Comments
agent_kruger 21-Feb-14 3:27am    
sir, without iteration [for,while,do while or foreach]
BillWoodruff 21-Feb-14 8:56am    
You are very confused. There is no way you will be able to search in the Win Form TreeView without doing iteration at least once to build-up an internal data-structure that allows "instant" search. And, that's what the code above illustrates.
agent_kruger 21-Feb-14 10:37am    
sir, can't we use "Nodes.ContainsKey" or "Nodes.Find" to find records?
BillWoodruff 21-Feb-14 14:20pm    
Please check out the revised content, and see if what I am saying is clearer to you now.

Over time I found the Microsoft TreeView Control very limiting, and, for many reasons, I purchased the excellent IntegralUI TreeView from Lidor Systems, which I use now, and which exposes a flattened list of TreeNodes, as well as implements on-demand partial loading so you can deal with extremely large collections of TreeNodes efficiently.

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900