CodeSnip: Convert.ChangeType Wrapper that Handles Nullable Types
page 1 of 1
Published: 22 May 2006
Unedited - Community Contributed
Abstract
Microsoft has confirmed that using the .NET Framework's Convert.ChangeType method doesn't handle nullable types. Until it does, here's a Convert.ChangeType wrapper you can use that does handle them.
by Peter Johnson
Feedback
Average Rating: This article has not yet been rated.
Views (Total / Last 10 Days): 26962/ 21

A known problem with the useful late-bound casting method Convert.ChangeType is that it doesn’t handle nullable types. I discovered this problem several months ago, talked to the CLR team at Microsoft about it, blogged about it, and have now written and tested a wrapper method that does handle nullable types. Hopefully, a future .NET Framework service pack will include this functionality, so this method can be deleted and calls to it can be changed to call Convert.ChangeType directly again.

Listing 1 – An improved ChangeType method

/// <summary>
/// Returns an Object with the specified Type and whose value is equivalent to the specified object.
/// </summary>
/// <param name="value">An Object that implements the IConvertible interface.</param>
/// <param name="conversionType">The Type to which value is to be converted.</param>
/// <returns>An object whose Type is conversionType (or conversionType's underlying type if conversionType
/// is Nullable&lt;&gt;) and whose value is equivalent to value. -or- a null reference, if value is a null
/// reference and conversionType is not a value type.</returns>
/// <remarks>
/// This method exists as a workaround to System.Convert.ChangeType(Object, Type) which does not handle
/// nullables as of version 2.0 (2.0.50727.42) of the .NET Framework. The idea is that this method will
/// be deleted once Convert.ChangeType is updated in a future version of the .NET Framework to handle
/// nullable types, so we want this to behave as closely to Convert.ChangeType as possible.
/// This method was written by Peter Johnson at:
/// http://aspalliance.com/author.aspx?uId=1026.
/// </remarks>
public static object ChangeType(object value, Type conversionType)
{
// Note: This if block was taken from Convert.ChangeType as is, and is needed here since we're
// checking properties on conversionType below.
  if (conversionType == null)
  {
    throw new ArgumentNullException("conversionType");
  } // end if
 
// If it's not a nullable type, just pass through the parameters to Convert.ChangeType
 
  if (conversionType.IsGenericType && 
    conversionType.GetGenericTypeDefinition().Equals(typeof(Nullable<>)))
  {
// It's a nullable type, so instead of calling Convert.ChangeType directly which would throw a
// InvalidCastException (per http://weblogs.asp.net/pjohnson/archive/2006/02/07/437631.aspx),
// determine what the underlying type is
// If it's null, it won't convert to the underlying type, but that's fine since nulls don't really
// have a type--so just return null
// Note: We only do this check if we're converting to a nullable type, since doing it outside
// would diverge from Convert.ChangeType's behavior, which throws an InvalidCastException if
// value is null and conversionType is a value type.
    if (value == null)
    {
      return null;
    } // end if
 
// It's a nullable type, and not null, so that means it can be converted to its underlying type,
// so overwrite the passed-in conversion type with this underlying type
    NullableConverter nullableConverter = new NullableConverter(conversionType);
    conversionType = nullableConverter.UnderlyingType;
  } // end if
 
// Now that we've guaranteed conversionType is something Convert.ChangeType can handle (i.e. not a
// nullable type), pass the call on to Convert.ChangeType
  return Convert.ChangeType(value, conversionType);
}

Special thanks to fellow ASPAlliance author J. Ambrose Little and alert reader Toby Johnson for helping me put together this method.



User Comments

Title: Mr   
Name: Glen
Date: 2012-01-25 3:54:19 PM
Comment:
chokes on boolean
Title: thanks   
Name: Natsy
Date: 2010-02-11 11:15:59 AM
Comment:
thanks a lot!!!!
Title: updates ??   
Name: enrique.prados@a-e.es
Date: 2009-11-03 8:59:30 AM
Comment:
Any updates about it ??

thanks in advanced
Title: Small Addition for GUID conversion Support   
Name: Eduardo Freitas
Date: 2009-03-27 11:12:08 AM
Comment:
Great Code !

I also needed to support GUID conversion, which currently throws an error when using ChangeType. So I added the following code to your function:

if (conversionType == typeof(System.Guid))
{
return new Guid(value.ToString());
}

just before the last return.

Thanks a lot !
Title: VB Equivalent   
Name: adrian
Date: 2009-02-26 12:10:26 PM
Comment:
I ussually write C#, but alas... I am stuck in VB land on this project... So here's the conversion ( note: haven't tested it yet )

Public Shared Function ChangeType(ByVal value As Object, ByVal conversionType As Type) As Object

If conversionType Is Nothing Then
Throw New ArgumentNullException("Conversion Type cannot be Null or Nothing")
End If

If conversionType.IsGenericType And _
conversionType.GetGenericTypeDefinition().Equals(GetType(Nullable)) Then

'-- RETURN NOTHING IF WE GOT NOTHING TO CONVERT --
If value Is Nothing Then
Return Nothing
End If

Dim nlConv As NullableConverter = New NullableConverter(conversionType)
conversionType = nlConv.UnderlyingType

End If

Return Convert.ChangeType(value, conversionType)
End Function

End Class
Title: A generic variant of your ChangeType method   
Name: Vladimir Kelman
Date: 2008-07-08 6:54:47 PM
Comment:
I modified your code slightly, to make it generic. Thanks!

http://pro-thoughts.blogspot.com/2008/07/generic-changetype-method-which-works.html
Title: Great work!   
Name: Erik
Date: 2008-04-16 4:44:19 AM
Comment:
Thank you for this simple, yet very useful code. I spent about 4 hours banging my head against the wall on trying to figure out why my application didn't want to convert a nullable variable.

Hopefully, Microsoft will add this functionality in one of their future updates to the framework.
Title: can we have this in vb.net code?   
Name: HyVong
Date: 2007-05-16 9:55:05 AM
Comment:
thanks for the helpful sample code, i was trying to convert them into vb.net but not very successful. Is there anyway we can have a vb.net version of this sample code?
Many thanks
Title: Simplification   
Name: dino
Date: 2006-11-04 1:43:22 AM
Comment:
good
Title: Simplification   
Name: Richard
Date: 2006-05-31 6:37:11 AM
Comment:
Instead of:

NullableConverter nullableConverter = new NullableConverter(conversionType);
conversionType = nullableConverter.UnderlyingType;

you can use:

conversionType = Nullable.GetUnderlyingType(conversionType);






Community Advice: ASP | SQL | XML | Regular Expressions | Windows


©Copyright 1998-2024 ASPAlliance.com  |  Page Processed at 2024-03-28 3:19:57 PM  AspAlliance Recent Articles RSS Feed
About ASPAlliance | Newsgroups | Advertise | Authors | Email Lists | Feedback | Link To Us | Privacy | Search