一尘不染

在带有linq而没有ToList()的foreach内时,数据库被锁定

sql

我尝试寻找答案,但找不到。“问题”很简单:

如果我使用linq收集项目,如下所示:

var items = db.AnyTable.Where(x => x.Condition == condition).ToList();

和另一个使用linq但没有的项目集合ToList()

var items2 = db.AnyTable.Where(x => x.Condition == condition);

如果现在我尝试使用foreach迭代每个项目(我没有尝试过while或没有其他迭代方法):

foreach (var item in items) 
{
    int i = 2;// Doesn't matter, The important part is to put a breakpoint here.
}

如果我在断点处停止代码,然后尝试更新AnyTableSQL Management Studio上的所有内容,则一切正常。但是如果!:

foreach (var item in items2) 
{
    int i = 2;// Doesn't matter, The important part is to put a breakpoint here.
}

如果现在我尝试更新(在断点上)AnyTable在SQL Management Studio上,我将无法执行更新(超时)。

为什么会ToList()产生如此不同?

从我了解到的一个特别的区别是查询的执行时间(在items声明items2中执行查询,在foreach语句中执行查询)。为什么这会阻止我进行更新AnyTable


阅读 133

收藏
2021-05-23

共1个答案

一尘不染

仅当您访问数据时,linq查询才会转换为SQL查询。当您调用ToList()时,您将创建一个SQL查询,该查询将所有数据从db返回到代码中。现在,项var完全位于内存中,不再需要对数据库做任何工作。在第二个示例中,您使用的是foreach,它将在数据库中打开一个事务,而在该事务仍处于打开状态时,您将尝试更改将获得超时的数据,因为该表由打开的LINQ查询保留数据库。

2021-05-23