实体框架核心:将多个结果对象组合到一个集合中

时间:2018-05-23 12:11:42

标签: entity-framework linq linq-to-sql linq-to-entities entity-framework-core

我正面临实体框架核心(2.0)的这个linq查询。

  var result = await dbContext.Table1DbSet
.Where(t1e => t1e.Id == id && t1e.Id2 == id2)
.Select
(
  t1e =>
  t1e.Table2NavPropICollection.Select
  (
    t2e => new
    {
      singleObject = t2e.Table3NavPropObject.TargetObject,
      enumerable1  = t2e.Table3NavPropObject.Table4NavPropObject.Table5NavPropICollection.Select(t5e => t5e.TargetObject),
      enumerable2  = t2e.Table3NavPropObject.Table6NavPropObject.Table7NavPropICollection.Select(t7e => t7e.TargetObject),
      enumerable3  = t2e.Table3NavPropObject.Table8NavPropICollection.SelectMany(t8e => t8e.Table9NavPropICollection.Select(t9e => t9e.TargetObject))
    }
  )
)
.ToListAsync();

目标是查询TargetObject的所有引用实例,这些实例被引用为~10个不同的表。

目前它返回一个IEnumerable,其中匿名对象包含属性singleObject,enumerable1,enumerable2,enumerable3。所有这些属性都是TargetObject或IEnumerable类型。

我可以,以及如何重写查询以不返回匿名对象,而只是包含所有值的IEnumerable?

由于某种原因,编译器不会让我迭代匿名集合并手动压平它。

2 个答案:

答案 0 :(得分:1)

如果你想要每个t1e行有一个数组,这应该可以解决问题。

      var result = await dbContext.Table1DbSet
    .Where(t1e => t1e.Id == id && t1e.Id2 == id2)
    .Select
    (
      t1e =>
      t1e.Table2NavPropICollection.Select
      (
        t2e => new[] {t2e.Table3NavPropObject.TargetObject}.Concat(
            t2e.Table3NavPropObject.Table4NavPropObject.Table5NavPropICollection.Select(t5e => t5e.TargetObject)).Concat(
            t2e.Table3NavPropObject.Table6NavPropObject.Table7NavPropICollection.Select(t7e => t7e.TargetObject)).Concat(
            t2e.Table3NavPropObject.Table8NavPropICollection.SelectMany(t8e => t8e.Table9NavPropICollection.Select(t9e => t9e.TargetObject)))
      )
    )
    .ToListAsync();

如果你想要它完全平坦,你需要将Select切换到SelectMany()。

      var result = await dbContext.Table1DbSet
    .Where(t1e => t1e.Id == id && t1e.Id2 == id2)
    .SelectMany
    (
      t1e =>
      t1e.Table2NavPropICollection.Select
      (
        t2e => new[] {t2e.Table3NavPropObject.TargetObject}.Concat(
            t2e.Table3NavPropObject.Table4NavPropObject.Table5NavPropICollection.Select(t5e => t5e.TargetObject)).Concat(
            t2e.Table3NavPropObject.Table6NavPropObject.Table7NavPropICollection.Select(t7e => t7e.TargetObject)).Concat(
            t2e.Table3NavPropObject.Table8NavPropICollection.SelectMany(t8e => t8e.Table9NavPropICollection.Select(t9e => t9e.TargetObject)))
      )
    )
    .ToListAsync();

答案 1 :(得分:0)

Add和/或Concat是否可能成为解决方案?

的PoC:

var a = new [] { 1,2,3 };

var result = new {
    firstA = a.First(),
    otherAs = a,
    backwards = a.Reverse()
};

var final = new List<int>();
final.Add(result.firstA);
final.Concat(result.otherAs.Concat(result.backwards))
    .Dump();