[英]My generic type converter smells bad, exceptions at runtime, object as catch all, boxing etc
首先, 我在其他地方問過這個問題 ,但是meta.stackoverflow.com似乎認為在其他地方問同樣的問題就可以了 ,所以這是可行的。 如果有答案,我會同時更新。
我在簡單類型之間做了很多轉換,我想盡可能地好處理它。 我認為會做這樣的事情會很好:
var converter = GetMySingletonConverterRegistryPlease();
var somePoint = GetMeSomePointFromSomewhereThanks();
converter.Register<Point, List<int>>(
point => new List<int>{ point.X, point.Y }
);
var someInts = somePoint.To<List<int>>();
因此,我提出了以下建議。 我對此一點都不滿意,並希望獲得一些建議(我將在代碼片段之后列舉為什么我不喜歡它)
public sealed class TypeConverterRegistry : TypeConverterRegistryBase {
public static readonly TypeConverterRegistry Instance = new
TypeConverterRegistry();
static TypeConverterRegistry() {}
TypeConverterRegistry() {}
}
public abstract class TypeConverterRegistryBase {
private readonly Dictionary<object, Delegate> _converters = new
Dictionary<object, Delegate>();
public void Register<TFrom, TTo>( Func<TFrom, TTo> converter ) {
var key = new { From = typeof( TFrom ), To = typeof( TTo ) };
_converters[ key ] = converter;
}
public TTo ConvertTo<TTo>( object from ) {
var key = new { From = from.GetType(), To = typeof( TTo ) };
if( !_converters.ContainsKey( key ) )
throw new KeyNotFoundException(
"No converter has been registered that takes a " + key.From +
" and returns a " + key.To );
var converter = _converters[ key ];
return (TTo) converter.DynamicInvoke( from );
}
}
public static class Extensions {
public static TTo To<TTo>( this object value ) {
return TypeConverterRegistry.Instance.ConvertTo<TTo>( value );
}
}
我不喜歡我在這里所做的事情,因為它不是強類型/受約束的,很容易意外地誤使用它並獲得運行時異常,我將對象用作全部捕獲對象,並且我也對我調用DynamicInvoke並將結果裝箱的方式。 你們無疑會看到更多的問題! 我也對在對象上使用擴展方法感到難過。
我做喜歡的是相應的語法!
因此,我非常感謝您提供的任何建議,即使只是朝着正確的方向前進。
或者放心,畢竟這不是一個壞方法:P
看一下AutoMapper(http://automapper.codeplex.com/)。 盡管意圖不同,但是您的項目具有很多共性,您可能可以從他們的模式和代碼中獲得很多好處。
在運行時異常方面,這可能歸結為單元測試,因為您依賴用戶在使用類型之前對其進行注冊。 沒有辦法解決,這與AutoMapper所做的相同,但是它們也提供了一些測試工具。
我強烈建議將ConvertTo方法重寫為通用的,以便from參數是通用的,而不是類型object 。 您可以這樣做:
public TTo ConvertTo<TFrom, TTo>( TFrom from ) {
var key = new { From = typeof( TFrom ) To = typeof( TTo ) };
if( !_converters.ContainsKey( key ) )
throw new KeyNotFoundException(
"No converter has been registered that takes a " + key.From +
" and returns a " + key.To );
var converter = _converters[ key ] as Func<TFrom, TTo>;
return converter(from);
}
這也可以解決擴展方法的問題。 您現在可以使用以下命令進行調用:
public static TTo Convert<TFrom, TTo>(this TFrom value){
return TypeConverterRegistry.Instance.Convert<TFrom, TTo>(value);
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.