C # clever use of extension methods Article 7: "Tree" generic Traversal

Source: Internet
Author: User
In my previous article "C # Extension Method whimsical use advanced Article 6: winform control selector", a winform selector is provided. Its essence is a "Tree" traversal tool, however, this traversal is limited to the control class of winform. In the data structure, "Tree" traversal is a general algorithm. Why do we not make a general "Tree" traversal extension?

 

Let's first look at a simple class people (which will be used as an example for testing ):

1 public abstract class people
2 {
3 Public bool ismale {Get; private set ;}
4 public abstract ienumerable <people> children {Get ;}
5}

The people class has a children attribute that returns all children of the people. The people class uses the children attribute to form a People Tree.

 

The general traversal extension of the "Tree" is as follows:

1 public static ienumerable <t> getdescendants <t> (this t root,
2 func <t, ienumerable <t> childselector, predicate <t> filter)
3 {
4 foreach (t in childselector (Root ))
5 {
6 if (filter = NULL | filter (t ))
7 yield return T;
8 foreach (T child in getdescendants (t) T, childselector, filter ))
9 yield return child;
10}
11}

Write several call examples using the people class:

1 people;
2 //
3 // obtain all descendants
4 var descendants = people. getdescendants (P => P. Children, null );
5 // obtain all male children
6 var males = people. getdescendants (P => P. Children, P => P. ismale );

Of course, there is another situation where only the children of this tribe can be obtained (Women in the children's family are married, not their children). This situation is a little complicated. This article focuses more on ideas, the sample code is no longer provided (which can be implemented by a friend and sent to the reply ).

Since it is common, let's use it in winform as a selector:

1 // form1.cs
2 // obtain all controls of this form
3 var controls = (this as control). getdescendants (C => C. Controls. Cast <control> (), null );
4 // obtain all the selected checkboxes
5 var checkboxes = (this as control). getdescendants (
6 c => C. Controls. Cast <control> (),
7 C => (C is checkbox) & (c as checkbox). Checked
8)
9. Cast <checkbox> ();

General Methods certainly do not have dedicated elegance in writing, and multiple is/As and cast are used, mainly because inheritance is involved here, and the type controlcollection of the Control. CONTROLS attribute is not a generic set.

 

The preceding two examples are similar: the "root" in the tree structure is of the same type (or has the same base class) as the "child", and the Treeview in winform is different: Treeview (Root) contains multiple treenode (child). Each treenode can also contain multiple treenode (child). The "root" and "child" types are different (and there is no same base class), such:

 

 

We need to use another extension (to call the above Extension Method ):

1 public static ienumerable <t> getdescendants <troot, T> (this troot root,
2 func <troot, ienumerable <t> rootchildselector,
3 func <t, ienumerable <t> childselector, predicate <t> filter)
4 {
5 foreach (t in rootchildselector (Root ))
6 {
7 if (filter = NULL | filter (t ))
8 yield return T;
9 foreach (T child in getdescendants (T, childselector, filter ))
10 yield return child;
11}
12}

The call code is as follows:

1 // obtain all Tree nodes ending with "Wine" in the Treeview
2 var treeviewnode = treeview1.getdescendants (
3 Treeview => Treeview. nodes. Cast <treenode> (),
4 treenode => treenode. nodes. Cast <treenode> (),
5 treenode => treenode. Text. endswith ("Wine ")
6 );

 

With these two extensions, I believe they can meet the requirements of most "Tree" traversal. For convenience, we can also perform some heavy loads.

In addition, the traversal of the "Tree" takes precedence over depth and breadth. Here, we will not give examples one by one.

 

Please stay tuned to my series of articles "C # great use of extension methods!

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.