【发布时间】:2012-07-05 05:34:01
【问题描述】:
当 AutoMapper 遇到一个已经被映射的对象时,它似乎会再次使用该对象,而不是尝试重新映射它。我相信它是基于.Equals() 做到这一点的。
我有一棵正在被映射的树。因此,一个具有一些属性和子节点的节点。多个节点具有相同的 .Equals() 值,因为它基于 Id 属性。节点的子节点不同,我需要重新映射这些节点,但它使用的是缓存的映射值。
有没有办法关闭缓存映射?我能想到的只是实现一个新的转换器,但这完全违背了使用 AutoMapper 的目的。
这是一个如何复制的示例。
void Main()
{
var source = new List<Tag>
{
new Tag
{
Id = 1,
Name = "Tag 1",
ChildTags = new List<Tag>
{
new Tag
{
Id = 2,
Name = "Tag 2",
ChildTags = new List<Tag>
{
new Tag {Id = 3, Name = "Tag 3"},
new Tag {Id = 4, Name = "Tag 4"}
}
}
}
},
new Tag { Id = 1, Name = "Tag 1" },
new Tag
{
Id = 3, Name = "Tag 3", ChildTags = new List<Tag>
{
new Tag {Id = 4, Name = "Tag 4"}
}
}
};
Mapper.CreateMap<Tag, Tag>();
var results = Mapper.Map<IList<Tag>, IList<Tag>>(source);
results.Dump();
}
public class Tag
{
public int Id { get; set; }
public string Name { get; set; }
public IEnumerable<Tag> ChildTags { get; set; }
public override bool Equals(Object obj)
{
if (obj == null)
{
return false;
}
var x = this;
var y = (Tag)obj;
return x.Id.Equals(y.Id);
}
public override int GetHashCode()
{
return Id.GetHashCode();
}
}
【问题讨论】:
-
我会尝试自己实例化 MappingEngine 并像上面所说的那样控制生命周期,看看是否能做到这一点。
-
所以,看起来我需要实现一个 ITypeMapFactory。这对我需要做的事情来说太多了。如果有一种简单的方法可以将其关闭,那就太好了,但看起来情况并非如此。如果您想创建此问题的答案并放入示例,我会将其标记为您的答案。
-
当您说“遇到一个已经被映射的对象”时,您是指映射配置(Mapper.CreateMap)还是实际映射(Mapper.Map)? Automapper 不缓存以前映射的实例(即不缓存 Mapper.Map 调用结果)。
-
将“等于”更改为不将具有相同 id 的项目视为同一对象是否有任何价值? (即,如果您的其余代码不依赖于它以某种方式工作,似乎它会修复它?)
标签: c# .net automapper