How to lookup and invoke a .Net TypeConverter for a particular type?

前端 未结 4 619
后悔当初
后悔当初 2020-12-28 22:06

I would like to implement a general purpose runtime type conversion function that makes use .Net TypeConverters to do the conversion.

Does anyone know how to how t

相关标签:
4条回答
  • 2020-12-28 22:13
        TypeConverter converter = TypeDescriptor.GetConverter(sourceType);
        if(converter.CanConvertTo(destinationType)) {
            return converter.ConvertTo(obj, destinationType);   
        }
        converter = TypeDescriptor.GetConverter(destinationType);
        if(converter.CanConvertFrom(sourceType)) {
            return converter.ConvertFrom(obj);
        }
    

    You could also look at Convert.ChangeType(obj, destinationType)

    0 讨论(0)
  • 2020-12-28 22:14

    I don't know how robust it is, but I sometimes use this code for generic type conversion :

    public T ConvertTo<T>(object value)
    {
        return (T)Convert.ChangeType(value, typeof(T));
    }
    

    I don't know if the ChangeType method use TypeConverters...

    0 讨论(0)
  • 2020-12-28 22:20

    Here's the code used in one of our existing apps... not sure if it's ideal but it works well for us.

    /// <summary>
    /// Attempts to convert a value using any customer TypeConverters applied to the member
    /// </summary>
    /// <param name="value">Object containing the value to be assigned</param>
    /// <param name="member">Member to be assigned to</param>
    /// <returns><paramref name="value"/> converted to the appropriate type</returns>
    public static Object CustomTypeConversion ( object value, MemberInfo member )
    {
        if ( value == null || value == DBNull.Value )
            return value;
    
        if ( member == null )
            throw new ArgumentNullException ( );
    
        List<TypeConverter> converters = GetCustomTypeConverters ( member );
    
        foreach ( TypeConverter c in converters )
        {
            if ( c.CanConvertFrom ( value.GetType ( ) ) )
                return c.ConvertFrom ( value );
        }
    
        if ( member is PropertyInfo )
        {
            PropertyInfo prop = member as PropertyInfo;
            return ConvertToNative( value , prop.PropertyType );
        }
        return ConvertToNative ( value, member.MemberType.GetType ( ) );
    }
    
    /// <summary>
    /// Extracts and instantiates any customer type converters assigned to a 
    /// derivitive of the <see cref="System.Reflection.MemberInfo"/> property
    /// </summary>
    /// <param name="member">Any class deriving from MemberInfo</param>
    /// <returns>A list of customer type converters, empty if none found</returns>
    public static List<TypeConverter> GetCustomTypeConverters ( System.Reflection.MemberInfo member )
    {
        List<TypeConverter> result = new List<TypeConverter>();
    
        try
        {
            foreach ( TypeConverterAttribute a in member.GetCustomAttributes( typeof( TypeConverterAttribute ) , true ) )
            {
                TypeConverter converter = Activator.CreateInstance( Type.GetType( a.ConverterTypeName ) ) as TypeConverter;
    
                if ( converter != null )
                    result.Add( converter );
            }
        }
        catch
        {
            // Let it go, there were no custom converters
        }
    
        return result;
    }
    
    /// <summary>
    /// Attempts to cast the incoming database field to the property type
    /// </summary>
    /// <param name="value">Database value to cast</param>
    /// <param name="castTo">Type to cast to</param>
    /// <returns>The converted value, if conversion failed the original value will be returned</returns>
    public static object ConvertToNative ( object value , Type castTo )
    {
        try
        {
            return Convert.ChangeType( value , castTo , System.Threading.Thread.CurrentThread.CurrentCulture );
        }
        catch
        {
            return value;
        }
    }
    

    Just call the CustomTypeConversion method and away you go... probably a little more than you need but being thorough isn't a crime (or is it?).

    0 讨论(0)
  • 2020-12-28 22:25

    In addition to Marc's answer, you might consider that ASP.NET's ViewState does a similar function to what you're asking to do. It tries to find the most efficient conversion.

    It might be worth a look at this page and possibly this one too.

    0 讨论(0)
提交回复
热议问题