将MyType类型映射到MyType时出现InvalidCastException

时间:2013-08-08 14:26:48

标签: c# generics automapper .net-4.5 automapper-2

我正在使用AutoMapper 2.2.1将不同的业务对象映射到视图模型。现在,如果我尝试映射具有InvalidCastExceptions类型属性的对象,我将获得CustomList(请参阅下面的代码)。 例外情况表明CustomList无法投放到IList。这是正确的,因为CustomList实现了IReadOnlyList而不是IList

那么为什么automapper会尝试以这种方式投射它以及如何修复/解决这个问题呢?

我有以下类型:

public class MyViewModel : SomeModel { //... some addtional stuff ...}

public class SomeModel {
public CustomList DescriptionList { get; internal set; }
}

public class CustomList : ReadOnlyList<SomeOtherModel> {}

public abstract class ReadOnlyList<TModel> : IReadOnlyList<TModel> {}

//map it
//aList is type of SomeModel 
var viewList = Mapper.Map<List<MyViewModel>>(aList);

1 个答案:

答案 0 :(得分:2)

从IReadOnlyList获取类实现很可能导致问题。 Automapper不知道如何将只读列表映射到只读列表。它创建了对象的新实例,并且没有IReadOnlyList的添加方法或集合初始值设定项。 Automapper需要能够访问readonly列表所包含的基础列表。这可以使用ConstructUsing方法完成。

更新了列表模型:

public class CustomList : IReadOnlyList<string>
{
    private readonly IList<string> _List;

    public CustomList (IList<string> list)
    {
        _List = list;
    }

    public CustomList ()
    {
        _List = new List<string>();
    }

    public static CustomList CustomListBuilder(CustomList customList)
    {
        return new CustomList (customList._List);
    }
}

更新了automapper配置

Mapper.CreateMap<CustomList, CustomList>().ConstructUsing(CustomList.CustomListBuilder);

这是一个简单的例子,但我能够正确地映射它并且不抛出异常。这不是最好的代码,这样做会导致同一个列表被两个不同的只读列表引用(取决于您的要求,可能会也可能不会)。希望这会有所帮助。