我已尝试This answer,This one和this one合并两个iqueryable。但我总是收到以下错误:
“Estudio”类型出现在单个LINQ to Entities查询中的两个结构不兼容的初始化中。可以在同一查询中的两个位置初始化类型,但前提是在两个位置都设置了相同的属性,并且这些属性的设置顺序相同。
我正在从两个不同但相似的实体框架实体(EXAMEN和EXPLORACION)映射到我的域实体Estudio,其代码如下。
IQueryable<Estudio> listExamen = context.Set<EXAMEN>().Project().To<Estudio>();
IQueryable<Estudio> listExploracion = context.Set<EXPLORACION>().Project().To<Estudio>();
var listCombined = listExamen.Concat(listExploracion);
无论如何使用两个列表的合并生成IQueryable(不可枚举)?如果使用 AsEnumerable(),则会在内存上执行以下过滤器(Order,Take等)。所以我需要合并列表,但仍然能够在不执行查询的情况下将过滤器应用于合并列表。
//This will force the next condition is executed on memory
var listCombined = listExamen.AsEnumerable().Concat(listExploracion);
这可能吗?
答案 0 :(得分:3)
我会尝试在您的linq查询中选择您的数据为匿名类型,执行联合并添加您的条件。
var listExamen = context.Examen
.Select(x => new { x.Prop1, x.Prop2, ... }); // Add properties
var listExploracion = context.Exploraction
.Select(x => new { x.Prop1, x.Prop2, ... }); // Add identical properties
var listCombined = listExamen.Concat(listExploracion);
var whereAdded = listCombines
.Where(x => x.Prop1 == someValue);
var result = whereAdded
.Skip(skipCount)
.Take(takeCount)
.ToList();
注意:我不知道你是否可以结合使用公用表格表达式(跳过/取得的SQL必要性)
注意:我已经更改了用于创建表达式的方法,因为我不知道您的方法(Project
,To
)
所以我认为解决方案不是转换为特定类型,而是转换为匿名类型,因为这可能会被转换为SQL。
警告:没有测试
答案 1 :(得分:3)
我的解决方案是修改我的映射代码。我不必使用单独的基于属性的映射器,而是必须立即投影整个实体,确保所有属性都以相同的顺序给出。
所以,而不是ForMember
语法:
Mapper.CreateMap<Client, PersonResult>()
.ForMember(p => p.Name, cfg => cfg.MapFrom(c => c.Person.FirstName + " " + c.Person.LastName))
...
我使用了ProjectUsing
语法:
Mapper.CreateMap<Client, PersonResult>()
.ProjectUsing(c => new PersonResult()
{
Name = c.Person.FirstName + " " + c.Person.LastName
...
});
这必须是因为AutoMapper构建其投影的方式。
答案 2 :(得分:0)
解决此问题的一种方法是添加虚拟类型:
class Estudio<T> : Estudio { }
新映射:
Mapper.CreateMap<Estudio , Estudio>();
Mapper.CreateMap<EXAMEN , Estudio<EXAMEN>>();
Mapper.CreateMap<EXPLORACION, Estudio<EXPLORACION>>();
有一点需要注意,Estudio
中的所有字段都需要映射中的某些值。
你不能使用忽略。返回0
或""
很好。
现在我们可以做到:
var a = context.Set<EXAMEN>().ProjectTo<Estudio<EXAMEN>>();
var b = context.Set<EXPLORACION>().ProjectTo<Estudio<EXPLORACION>>();
return a.ProjectTo<Estudio>().Concat(b.ProjectTo<Estudio>());