使用相同的数据库上下文运行多个选择查询

时间:2018-11-30 23:47:08

标签: asp.net-mvc entity-framework entity-framework-4

您可以使用相同的数据上下文运行多个“选择”查询吗?今天在工作中,我遇到一种情况,当我使用Entity Framework 4在同一上下文中运行多个“选择”查询时,查询返回的结果不准确。代码类似于以下代码:

if ($row['totalcount'] >0)

所以我发生的事情是v2包含了v1的先前结果。我怀疑这是因为上下文直到此using块结束才被释放。我想知道将来是否要避免此错误,所以我应该在每次查询后处理上下文。

2 个答案:

答案 0 :(得分:0)

DataContext的变更跟踪器会累积您在DataContext的生存期内获取的所有实体。变更跟踪器将“修正”在单独查询中获取的实体之间的关系。因此,在检查导航属性时,您可能会看到以前查询的结果。

但这不会影响您发布的代码。另外,您应该使用EF 6,而不是EF 4。

答案 1 :(得分:0)

DbContext会记住您已经获取的项目。为了能够在保存之前更改获取的数据,这是必需的。

示例: 假设您有一所学校,有很多老师和很多学生;每个老师有零个或多个学生,每个学生有零个或多个老师(多对多关系)

假设学生[100]叫特蕾莎(Theresa),并居住在“唐宁街10号,伦敦”,她在移动。同时,您想将她的新地址通知附近的所有其他学生:

var TheresaMay = dbContext.Students.
    .Where(student => student.Id == 100)
    .FirstOrDefault();

// change address of TheresaMay:
theresaMay.Address = "King's College, Oxford",

数据尚未保存,她仍然住在伦敦的数据库中。如果使用此值,您想要什么?更改后的值或数据库值:

var city = theresaMay.City; // London or Oxford?

将她的新地址通知附近的所有学生

var nearbyStudents = dbContext.Students
    .Where(student => student.City == theresaMay.City)
    .ToList();
SendMessage(nearbyStudents)

您想让牛津大学的学生获得通知,还是想要伦敦的学生?

假设您要获取按城市分组的学生:

var studentsGroupedByCitry = dbContext.Students
    .GroupBy(student => student.City)
    .ToList();

问题:伦敦学生或牛津学生中应该有吗?

实体框架的设计者认为这是明智的,一旦您获取了TheresaMay并更改了一个属性,对您来说,该属性的值将是新值,而不是数据库中仍然存在的值。

因为我们不知道您是否成功保存了更改,所以其他将获取TheresaMay的人仍然可以获取数据库值。

因此,保持上下文开放状态以查询多个项目有点危险,因为如果其他人更改了您已获取的项目之一,您将不会看到这些更改。因此,仅在真正需要的时间保留dbContext是明智的。通常,这大约是您通常会锁定数据库的时间或使事务保持活动的时间。