There are times when you have to copy each property of an object to one another. This is called mapping and it's very fastidious to do it by hand.
In this post, we'll see how to create a method extension which does it for you in one line of code!
When Can It Be Useful
Here is a non exhaustive list of usage you can find to this snippet:
- You want to reload the previous state of an object without changing its instance: just clone it as a snapshot and copy back the properties when you want.
- You get some Data Transfer Object coming from WCF/Web services and you want to fill a specific object with this data.
- etc.
I surely know this is not the most efficient way to solve these problems, but this is fast to use/understand and easy to implement.
Let's Jump to the Code !
What's inside? Quite a few things actually! There are two objects, the source in which we take the data and the target in which we fill in the data.
I use reflection to obtain every property of the source and then I check on the target if a property exists with the same name. If yes, I fill it with the value of the property in the source object.
I also added a filter which is a list of Property names which will be ignored by the "copy process".
With a little more time, you can also add a dictionary
which may map a property name in the source to another property name in the target if the names are noted to be exactly the same...
public static class PropetiesMapper{
public static void copyPropertiesFrom
(this object to, object from, string[] excludedProperties)
{
Type targetType = to.GetType();
Type sourceType = from.GetType();
PropertyInfo[] sourceProps = sourceType.GetProperties();
foreach (var propInfo in sourceProps)
{
if (excludedProperties != null
&& excludedProperties.Contains(propInfo.Name))
continue;
PropertyInfo toProp =
(targetType == sourceType) ? propInfo : targetType.GetProperty(propInfo.Name);
if (toProp != null && toProp.CanWrite)
{
Object value = propInfo.GetValue(from, null);
toProp.SetValue(to,value , null);
}
}
}
public static void copyPropertiesFrom(this object to, object from)
{
to.copyPropertiesFrom(from, null);
}
public static void copyPropertiesTo(this object from, object to)
{
to.copyPropertiesFrom(from, null);
}
public static void copyPropertiesTo
(this object from, object to, string[] excludedProperties)
{
to.copyPropertiesFrom(from, excludedProperties);
}
}
So, do you still want to put a "Hand made" label on your object's mapping ?
A More Complex and Complete Tool
For those who want something more powerful and complete, take a look at the automapper library on CodePlex.
CodeProject