我正在通过存储库模式使用实体框架,并且有一个重要且令人惊讶的性能问题。我已经完成了分析,所以我对发生的事情有一个很好的了解,我只是不知道该怎么做。
这是我的代码的本质(简化):
var employee = Repositories.Employees.FirstOrDefault(s => s.EmployeeId == employeeId);
employee.CompanyId = null;
Repositories.Commit();
中间线 ( employee.CompanyId = null
) 需要惊人的时间才能完成(大约 30 秒)。时间没有花在 Commit 行上。
通过分析,我找到了运行这部分自动生成的 EF 代码的原因:
if (previousValue != null && previousValue.**Employees**.Contains(this))
{
previousValue.Employees.Remove(this);
}
这并没有真正帮助我,但它确实证实了问题出在 EF 上。我真的很想知道该怎么做。我可以以其他方式(存储过程)更新列,但我真的更愿意在任何地方使用 EF。
我无法轻松编辑 EF 设置,因此我更喜欢不涉及此内容的建议。
更新 我通过直接对数据库运行 SQL 解决了这个问题,然后从上下文中刷新对象以确保 EF 会立即检测到此更改。
public void SetCompanyNull(Guid employeeId)
{
_ctx.ExecuteStoreCommand("UPDATE Employee SET CompanyId = NULL WHERE EmployeeId = N'" + employeeId + "'");
_ctx.Refresh(RefreshMode.StoreWins, _ctx.Employees.FirstOrDefault(s => s.EmployeeId == employeeId));
}
更新 2 我还通过暂时禁用延迟加载解决了这个问题。
var lazyLoadDisabled = false;
if (_ctx.ContextOptions.LazyLoadingEnabled)
{
_ctx.ContextOptions.LazyLoadingEnabled = false;
lazyLoadDisabled = true;
}
this.GetEmployeeById(employeeId).CompanyId = null;
this.SaveChanges();
if (lazyLoadDisabled)
{
_ctx.ContextOptions.LazyLoadingEnabled = true;
}
我真的很好奇为什么禁用延迟加载会更快(以及这可能有哪些副作用)