【发布时间】:2015-11-03 11:30:41
【问题描述】:
我有一个 LINQ 查询,我在优化时遇到了问题,运行大约需要 5.5 秒。我正在使用一个名为 StaffingResourceData 的视图和一个名为 StaffingForecasts 的表。
每个 StaffingResource 都有一个 ResourceId、一个部门和一个类型。 StaffingForecast 具有 ResourceId、Project、Date(表示一周中的星期一)、Hours。一个 StaffingResource 可以有 0 个 StaffingForecast。
对于每个 StaffingResource,我需要他们未来 12 周的总预测小时数列表。这是我现在拥有的:
// Get list of dates
var dates = new List<DateTime>();
var start = Utilities.GetStartOfWeek(DateTime.Today);
for (var i = 0; i < 12; i++)
{
dates.Add(start.AddDays(i * 7));
}
var end = dates[11];
// Get resources
var resources = (from r in context.StaffingResourceDatas
where r.EmployeeId != null
&& !exclusionList.Contains(r.ResourceTitleId)
join f in context.StaffingForecasts.Where(x => x.Date >= start && x.Date <= end) on r.ResourceId equals f.ResourceId into g1
from f in g1.DefaultIfEmpty()
group new { f.Date, f.Hours } by r into g2
select new ChartResourceModel
{
ResourceId = g2.Key.ResourceId,
Division = g2.Key.ResourceDivision,
Type = g2.Key.ResourceType,
Dates = dates.Select(d => new ChartDateModel
{
Date = d,
Available = (g2.Where(f => f.Date == d).Any() ? g2.Where(f => f.Date == d).Sum(f => f.Hours) : 0) < 24
}).ToList()
})
.ToList();
关于如何加快速度的任何想法?
【问题讨论】:
-
Code Review 会更好吗?
-
好吧,如果没有真正回答你的问题,你可以用
Any的重载替换这个Where(f => f.Date == d).Any()Func:Any(f => f.Date == d) -
看看正在生成的 SQL,这至少会给你一个开始。
-
group new { f.Date, f.Hours } by r into g2的部分看起来很可疑,我从未见过这样的东西,也不知道它是做什么的。 -
复杂的报告查询应该在视图中完成,而不是在 LINQ 中。加入 LINQ 意味着模型中缺少关系。添加关系,删除连接,让 EF 生成正确的 SQL。还要删除内部的
ToList()调用,它们会导致为每个日期执行单独的查询。您的代码可能会产生 1000 个查询而不是 1 个。
标签: c# performance entity-framework linq