在将列表传递给LINQ时调用单个数据库
本文关键字:调用 单个 数据库 LINQ 列表 | 更新日期: 2023-09-27 18:13:05
我得到一个电子邮件地址数组,对于每个电子邮件地址,我需要返回与该电子邮件地址相关的成员的numTotal和numActive。
传统上,我会从成员表中查询并过滤成员的电子邮件地址是否存在于传入的email数组中。但是,这只会返回电子邮件地址列表,其中包含成员表中存在的电子邮件的计数。相反,我需要记录每个提供的电子邮件地址,而不管成员是否拥有该电子邮件地址。
我的解决方案是遍历电子邮件数组,然后做一个子查询。这是有效的,我能够得到我需要的,但是当我配置调用时,我看到EF正在为每个电子邮件地址/子查询运行单独的查询。
var result = (from email in emailAddresses
select new EmailAddressStats {
Total = membersQueryable.Any(m => m.Email == email),
Active = membersQueryable.Any(m => m.Email == email && m.IsActive)
}).ToList();
所以如果我传递3个电子邮件地址,我看到6个单独的查询(3个电子邮件地址* 2个子查询)。
我已经尝试使用.AsQueryable()
使数组可查询,但我仍然得到相同的结果。
理想情况下,我希望EF生成如下内容:
SELECT ([totalSubquery]) AS Total,
([activeSubquery]) AS Active
FROM ????
WHERE EXISTS ('email1@domain.com', 'email2@domain.com', 'email3@domain.com' )
注意:我使用实体框架4
我没有安装EF4,但你应该能够这样做,只执行一个查询。
List<EmailAddressStats> GetEmailAddressStats(string[] emailAddresses)
{
var returnList = emailAddresses.Select(e => new EmailAddressStats { Email = e })
.ToList();
// I don't know what your context is actually called so I'm just calling it MemberDatabaseContext)
using (var dbContext = new MemberDatabaseContext())
{
// Query the database once with a single query to get all of the relevant members
var membersWithEmailAddress = dbContext.Members.Where(m => emailAddresses.Contains(m.Email))
.Select(m => new { Email = m.Email, IsActive = m.IsActive })
.ToList();
// Update the email stats by analyzing the member info in memory
foreach (var emailStat in returnList)
{
emailStat.Total = membersWithEmailAddress.Count(m => m.Email == emailStat.Email);
emailStat.Active = membersWithEmailAddress.Count(m => m.Email == emailStat.Email && m.isActive);
}
}
return returnList;
}
(对不起,这是在流利的语法,而不是查询表达式语法,但我只知道如何做到这在流利的语法)