BlackWaspTM

This web site uses cookies. By using the site you accept the cookie policy.This message is for compliance with the UK ICO law.

Reflection
.NET 1.1+

Accessing Field and Property Values with Reflection

The nineteenth part of the Reflection tutorial expands upon the previous instalment that dealt with instantiating late-bound types. This article looks at the methods that allow reflected field and property values to be read and changed using reflection.

Accessing Late Bound Object State

In the previous instalment in this tutorial we looked at how classes can be instantiated at run time using late binding, allowing the activation of objects of types that are unknown when your software is compiled. This is useful when you want to create a plug-in system to allow your software to be extended, or where you want to be able to substitute assemblies without the requirement to recompile your application.

When you use the Activator class to create late-bound objects, the results are instances of the System.Object class. If you know the actual type, or you know an interface that the type implements, you can cast the created object to another type in order to access its members in a strongly-typed manner. However, in many situations this will not be the case. You may not even know what methods and properties the activated object has, except that their names may be provided via configuration. To access the members, you must use reflection techniques.

In this article we'll look at how the fields and properties of late-bound and early-bound objects can be read and updated using reflection. To demonstrate we'll use the following sample class, which represents a person. The class includes public and private fields, and read-only and write-only properties. Add the class to a console application and execute the other examples from the Main method. In a real late-bound scenario the samples and the late-bound class would likely be in separate assemblies. For simplicity we'll keep them in a single project in this article.

public class Person
{
    public static int _counter = 10;
    private string _firstName, _lastName;

    public string FirstName
    {
        set { _firstName = value; }
    }

    public string LastName
    {
        set { _lastName = value; }
    }

    public string FullName
    {
        get { return string.Format("{0} {1}", _firstName, _lastName); }
    }
}

The code that we'll be using uses types from the System.Reflection namespace so include the following using directive:

using System.Reflection;

Setting Property Values

Let's start by looking at how to set property values of objects using reflection. You do this by first using reflection to obtain a PropertyInfo object representing the property that you wish to change. You then use the SetValue method to update the property. This method accepts three parameters. The first is the object that you wish to modify. The second is the new value, which is passed as a simple object. The third property is used for indexed properties and allows you to pass the index values as an object array. As our test class's properties are not indexed, we don't need to provide a third argument so will pass null.

The following code creates an instance of the Person object using late-binding. The third line gets the details of the FirstName property and the final statement changes the value of the property to "Bob" using the SetValue method. To test the code, execute it in the debugger and look at the property values in debug windows such as Locals or Autos.

Type type = typeof(Person);
object lateBound = Activator.CreateInstance(type);

PropertyInfo firstNameProperty = type.GetProperty("FirstName");
firstNameProperty.SetValue(lateBound, "Bob", null);

Reading Property Values

Reading property values is similar to changing those values. This time we use the GetValue method. The first parameter is the object to interrogate and the second provides the index information for indexed properties. Again, we'll use null for this as we don't have an indexed property. The return value of GetValue is an object that can be cast as required.

The following code demonstrates the use of GetValue by first creating a new Person and setting the first and last names. Finally, the code obtains the PropertyInfo object for the FullName property, reads the value using reflection and outputs the value to the console.

Type type = typeof(Person);
object lateBound = Activator.CreateInstance(type);

PropertyInfo firstNameProperty = type.GetProperty("FirstName");
firstNameProperty.SetValue(lateBound, "Sue", null);

PropertyInfo lastNameProperty = type.GetProperty("LastName");
lastNameProperty.SetValue(lateBound, "Black", null);

PropertyInfo fullNameProperty = type.GetProperty("FullName");
string name = (string)fullNameProperty.GetValue(lateBound, null);
Console.WriteLine(name);

/* OUTPUT

Sue Black

*/
30 July 2012