C# Linq到对象-傻瓜?

C# Linq到对象-傻瓜?,c#,.net,linq,linq-to-objects,C#,.net,Linq,Linq To Objects,我认为LINQtoObjects是连接数据的不同执行的好方法。事实上,这是一种糟糕的做事方式 这是我们所拥有的,在a、b、c、d中有少量、数百条、3K和3.5K记录 IEnumerable<MyModel> data = (from a in AList from b in BList.Where(r => r.AId == a.Id) from c in CList.Where(r => r.BId == b.Id) from d

我认为LINQtoObjects是连接数据的不同执行的好方法。事实上,这是一种糟糕的做事方式

这是我们所拥有的,在
a、b、c、d
中有少量、数百条、3K和3.5K记录

IEnumerable<MyModel> data =
    (from a in AList
     from b in BList.Where(r => r.AId == a.Id)
     from c in CList.Where(r => r.BId == b.Id)
     from d in DList.Where(r => r.SomeId == myId && r.Some2Id == c.Some2Id)
 //  . . . . . . 
IEnumerable数据=
(来自一位作家)
从BList.Where中的b开始(r=>r.AId==a.Id)
从CList.Where中的c开始(r=>r.BId==b.Id)
其中(r=>r.SomeId==myId&&r.Some2Id==c.Some2Id)
//  . . . . . . 
林克不是应该做得很棒吗? 事实上,跟随的速度要快得多,实际上快了60倍

var dTemp = DList.Where(r => r.SomeId == myId).ToList();
var cTemp = CList.Where(c => dTemp.Any(d => d.Some2Id == c.Some2Id)).ToList();

IEnumerable<MyModel> data =
    (from a in AList
     from b in BList.Where(r => r.AId == a.Id)
     from c in cTemp.Where(r => r.BId == b.Id)
 //  . . . . . .
var dTemp=DList.Where(r=>r.SomeId==myId.ToList();
var cTemp=CList.Where(c=>dTemp.Any(d=>d.Some2Id==c.Some2Id)).ToList();
IEnumerable数据=
(来自一位作家)
从BList.Where中的b开始(r=>r.AId==a.Id)
从cTemp.Where中的c开始(r=>r.BId==b.Id)
//  . . . . . .
然后我发现

问:有没有一种方法可以在不放弃单个LINQ的情况下改进此查询


或者这是否意味着,如果性能受到影响,需要避免以联接形式对对象执行LINQ,并用一些顺序调用来替换它?

让我们分析一下差异

第一次查询:您在
BList
上执行一个筛选器,在
CList
上执行一个筛选器,在
DList
上执行两个筛选器,所有这些都是以延迟执行的方式执行的。然后您使用一种联接。
第二次查询:在
DList
上执行静态筛选并对其求值,在
CList
上基于
DList
执行另一个静态筛选并对其求值,然后在
AList
BList
上执行延迟筛选

第二个查询更快,因为:

  • DList
    未查看无用值(由于以前的筛选器)
  • CList
    仅包含由于以前的筛选器而产生的有用值
无论如何,这两个查询都是错误的。来自的多个
基本上是一个
交叉连接
。正如@Reddog评论的那样,最好的方法是实际使用
连接

var data = from a in AList
           join b in BList on a.Id equals b.AId
           join c in CList on b.Id equals c.BId
           join d in DList on c.Some2Id equals d.Some2Id
           where d.SomeId == someId;

看起来你在尝试内部连接<代码> < <代码> >代码> b>代码>和<代码> c>代码>你试过使用函数而不是<>代码> ?考虑对你的LINQ进行积极的攻击。“我是绝对正确的,所以框架必须被打破”通常不是最好的开始位置。@EdPlunkett。我从来没有说它坏了。但是看起来,既然需要优化器,它就不太适合做这个job@Reddog是的,现在我们正在对此进行优化。这只是一种不好的做法。在某些情况下,它的工作原理是相同的,但是
join
是快速的。你是对的。在某些情况下,从
的工作原理与join中的
相同。对于小数据集,我们从来没有遇到过问题。但是这一个客户端有一个独特的设置,其中有大的[巨大的]在
c
d
中设置,它做得不太好。即使如此,它也不坏-140毫秒,但在该设置下它被重复运行。所以140x20…现在是2毫秒。2x20-非常不同的结果。我们以前会对其进行调整,但我们针对缓存数据替换的SQL调用进行了基准测试,结果很好。因此,没有人关注一个小小的事实。谢谢