내가 TypeConverter 물건 갈 것입니다. 그것은 기본적으로 가치와 문화 간의 전환을하는 클래스입니다. TypeConverter와 Convert.ChangeType의 주된 차이점은 소스 형식에서 IConvertible 인터페이스가 필요하고 TypeConverters는 모든 개체에서 작동 할 수 있다는 것입니다.
나는 종종 XML 파일에 다른 구성 객체를 저장하기 때문에 이것을위한 도우미 클래스를 만들었습니다. 또한 CultureInfo.InvariantCulture로 /에서 변환하기 위해 하드 코드 된 이유입니다.
public static class TypeConversion {
public static Object Convert(Object source, Type targetType) {
var sourceType = source.GetType();
if (targetType.IsAssignableFrom(sourceType))
return source;
var sourceConverter = TypeDescriptor.GetConverter(source);
if (sourceConverter.CanConvertTo(targetType))
return sourceConverter.ConvertTo(null, CultureInfo.InvariantCulture, source, targetType);
var targetConverter = TypeDescriptor.GetConverter(targetType);
if (targetConverter.CanConvertFrom(sourceType))
return targetConverter.ConvertFrom(null, CultureInfo.InvariantCulture, source);
throw new ArgumentException("Neither the source nor the target has a TypeConverter that supports the requested conversion.");
}
public static TTarget Convert<TTarget>(object source) {
return (TTarget)Convert(source, typeof(TTarget));
}
}
이 System.Version 같은 시스템 유형을, (IConvertible을 구현 나던하는) 실제 버전 개체에 버전 번호 ("ABCD")를 포함하는 문자열에서 같은 변환을 지원하기 위해 처리하기 위해 자신의 TypeConverter가를 만들 완전히 가능 .
public class VersionTypeConverter : TypeConverter {
public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType) {
if (sourceType == typeof(string))
return true;
return base.CanConvertFrom(context, sourceType);
}
public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value) {
var s = value as string;
if (s != null)
return new Version(s);
return base.ConvertFrom(context, culture, value);
}
public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType) {
if (destinationType == typeof(string))
return true;
return base.CanConvertTo(context, destinationType);
}
public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType) {
var v = value as Version;
if (v != null && destinationType == typeof(string)) {
return v.ToString();
}
return base.ConvertTo(context, culture, value, destinationType);
}
}
실제로 사용자 정의 TypeDescriptionProvider 및 typeof(Version)
전달 TypeDescriptor.AddProvider을 사용하면 응용 프로그램 시작시 등록이 필요이 공급자를 사용합니다. 이 경우 TypeDescriptorProvider.GetTypeDescriptor 메서드에서 사용자 지정 CustomTypeDescriptor을 반환해야하며 설명자는 GetConverter를 재정 의하여 VersionTypeConverter의 새 인스턴스를 반환해야합니다. 쉬운. ;)
Convert.ChangeType은 소스가 이미 필수 유형이 아닌 한 IConvertible을 구현하려면 소스 객체가 필요합니다. – sisve
XAttribute에서 (XmlConvert의 메서드를 사용하여) 정방향 변환이 수행되었지만 변환으로 변환이 역전 될 위험이 있습니까? 예를 들어 DateTime과 같은 변환이 다를 수있는 코너 케이스가 있는지 나는 알지 못합니다. –
예! 그것은 지금 당장 완벽하게 작동합니다. 고맙습니다! 그러나 예를 들어, 가상의 classA로 내 메서드를 사용할 수 없다는 것을 어떻게 확신 할 수 있는가? 왜냐하면 dint는 문자열에서의 변환이 존재하기 때문이다. 내가'T : IConvertible'을 단순히 지정하는 것이 옳지 않다는 것을 이해함에 따라 충분한 결과가 나오지 않을 것입니다. –