从匹配对象的列表中获取DbSet中的实体

10 浏览
0 Comments

从匹配对象的列表中获取DbSet中的实体

我正在使用Entity Framework Core 6,想要在一个DbSet中找到一系列的实体。我想要获取的实体是与输入对象列表中的一些属性匹配的实体。

我尝试了类似于以下的代码:

public IEnumerable FindEntities(IEnumerable entries)
{
    return dbContext.MyDbSet.Where(r => entries.Any(e => e.Prop1 == r.Prop1 && e.Prop2 == r.Prop2));            
}

但是我得到了经典的EF Core异常,提示我的LINQ无法转换为数据库查询(具体问题在于entries.Any(...)这条指令)

我知道我可以循环遍历entries列表,并从DbSet中逐个获取实体,但这样做速度非常慢,我想知道在EF Core中是否有更高效的方法来实现这个功能。

0
0 Comments

在这段对话中,讨论了如何从DbSet中获取与给定对象列表匹配的实体的问题。首先,提供了一种解决方法,即使用Select方法选择需要匹配的属性,并使用Contains方法进行过滤。然而,其他人认为这种方法并不能实现他们想要的功能。他们指出,这种方法只是检查给定的对象列表中是否存在满足条件的实体,但并不能保证它们是相同的实体。

为了解决这个问题,某些情况下了使用EF的IN和NOT IN操作符来实现只传递值列表的方法。但是,另一个人指出,使用||操作符代替&&操作符时,可能会导致不可预测的结果。

最后,有人指出这是一个相当困难的问题,并提供了一个相关的问题和答案的链接,以供进一步参考。

总之,从这段对话中可以看出,问题的出现是因为原始解决方法不能保证返回的实体与给定的对象是相同的。为了解决这个问题,可能需要进一步研究和尝试其他方法。

0
0 Comments

原因:从DbSet获取与给定对象列表匹配的实体的问题是因为在数据库中进行查询时,需要根据指定的键值来获取相应的实体。然而,如果直接使用foreach循环遍历列表中的每个对象并逐个查询,效率会降低,因为每次查询都需要与数据库进行交互。为了提高效率,需要一种更有效的方法来获取匹配的实体。

解决方法:为了解决这个问题,我编写了一个扩展方法GetRangeByKey,它接受一个DbSet和一个要查找的对象列表作为参数。首先,我使用toFind列表中的对象构建了一个HashSet,以便快速查找。然后,我使用循环将keys列表分成多个较小的块,每个块的大小为1000个键值。接下来,我使用Where查询在数据库中查找与当前块中的键值匹配的实体。如果是第一个查询结果,我将其赋值给result变量,否则我将查询结果与之前的结果进行连接。最后,将所有匹配的实体作为结果返回。

这种方法的优点是使用HashSet进行快速查找,避免了逐个查询的低效率。另外,将查询分成多个较小的块可以避免IN子句中的值过多导致数据库引擎拒绝查询的问题。

通过编写扩展方法GetRangeByKey,我们可以从DbSet中获取与给定对象列表匹配的实体。该方法使用HashSet进行快速查找,并将查询分成多个较小的块,以提高效率。这种方法可以有效地解决在数据库查询中获取匹配实体的问题。

0