CHAPTER 15 TYPE REFLECTION, LATE BINDING, AND ATTRIBUTE-BASED PROGRAMMING
Building a Custom Metadata Viewer
To illustrate the basic process of reflection (and the usefulness of System.Type), let’s create a Console
Application named MyTypeViewer. This program will display details of the methods, properties, fields,
and supported interfaces (in addition to some other points of interest) for any type within mscorlib.dll
(recall all .NET applications have automatic access to this core framework class library) or a type within
MyTypeViewer itself. Once the application has been created, be sure to import the System.Reflection
namespace.
// Need to import this namespace to do any reflection!
using System.Reflection;
Reflecting on Methods
The Program class will be updated to define a number of static methods, each of which takes a single
System.Type parameter and returns void. First you have ListMethods(), which (as you might guess)
prints the name of each method defined by the incoming type. Notice how Type.GetMethods() returns an
array of System.Reflection.MethodInfo objects, which can be enumerated over using a standard foreach
loop, as follows:
// Display method names of type.
static void ListMethods(Type t)
{
Console.WriteLine("***** Methods *****");
MethodInfo[] mi = t.GetMethods();
foreach(MethodInfo m in mi)
Console.WriteLine("->{0}", m.Name);
Console.WriteLine();
}
Here, you are simply printing the name of the method using the MethodInfo.Name property. As you
might guess, MethodInfo has many additional members that allow you to determine whether the method
is static, virtual, generic, or abstract. As well, the MethodInfo type allows you to obtain the method’s
return value and parameter set. You’ll spruce up the implementation of ListMethods() in just a bit.
If you wish, you could also build a fitting LINQ query to enumerate the names of each method.
Recall from Chapter 12, LINQ to Objects allows you to build strongly typed queries that can be applied to
in-memory object collections. As a good rule of thumb, whenever you find blocks of looping or decision
programming logic, you could make use of a related LINQ query. For example, you could rewrite the
previous method as so:
static void ListMethods(Type t)
{
Console.WriteLine("***** Methods *****");
var methodNames = from n in t.GetMethods() select n.Name;
foreach (var name in methodNames)
Console.WriteLine("->{0}", name);
Console.WriteLine();
}
564