从扩展方法中消除可推断的泛型类型参数

时间:2012-08-03 09:46:33

标签: c# .net generics automapper

我在我的应用程序中使用.NET映射库AutoMapper,我有一个像这样的通用扩展方法:

public static T2 Map<T1, T2>(this T1 o)
{
    return Mapper.Map<T1, T2>(o);
}

...

var nc = new NonCustomer();
Customer c = nc.Map<NonCustomer, Customer>();

有什么方法可以从扩展方法中删除T1泛型参数,以便推断它?导致这样的电话:

var nc = new NonCustomer();
Customer c = nc.Map<Customer>();

5 个答案:

答案 0 :(得分:3)

不,没有办法。通用类型推断不适用于返回类型。这种方式使您的扩展方法的有用性值得怀疑。为什么不直接使用.Map<TSource, TDest>方法?

答案 1 :(得分:3)

您不需要为T1参数使用通用版本。

您只需将其更改为对象:

public static TDest Map<TDest>(this object o)
{
    // todo check o is not null
    return (TDest) Mapper.Map(o, o.GetType(), typeof (TDest));
}

如果您使用的是AutoMapper v2及更高版本,则可以按如下方式编写:

public static TDest Map<TDest>(this object o)
{
    return Mapper.Map<TDest>(o);
}

答案 2 :(得分:1)

好问题。我一直懒得为自己解答,但那时鞋匠的孩子总是得到延伸方法......

你可以让它变得有点干涩,并且可以说是一个更漂亮的方面,一步一步地做一个推理:

public static MapperSource<T> Mapper(this T that)
{
    return new MapperSource<T>( that);
}

public class MapperSource<T>
{
    public T2 To<T2>
    {
        return Mapper.Map<T,T2>();
    }
}

允许您:

var nc = new NonCustomer();
Customer c = nc.Mapper().To<Customer>();

一种更常见的方式(对我而言)消耗它们是为每条Mapper.CreateMap'路线设置帮助,如下所示:

public static Customer ToResult(this NonCustomer that)
{
    return that.Mapper().To<Customer>();
}

(可悲的是因为没有扩展属性,它不能比这更漂亮。再说一次,当我们都使用F#时,一切都没有意义)

答案 3 :(得分:0)

不,你不能,因为在c#中没有部分类型推断这样的东西。

答案 4 :(得分:0)

仅当您完全删除T1泛型类型并为NonCustomer编写特定方法时才会这样做:

public static T2 Map<T2>(this NonCustomer o)
{
    return Mapper.Map<NonCustomer, T2>(o);
}