如何在Entity Framework linq查询中注入OR条件?

时间:2017-11-05 07:45:43

标签: c# entity-framework linq

我有两个或更多if条件来注入我的主查询但是如果条件没有值(可以为空)我不想注入我的查询。

例如,这是我的AND查询注入:

// first initialize query can have where or not
var query = context.QuestionInfoes.Include(x =>x.RelationsInfoes).AsQueryable();

// first if condition to inject query
if (filterQuestionInfo.ToProfileId.HasValue)
{
    query = (from q in query 
             join qr in context.QuestionRelationsInfoes on q.Id equals qr.QuestionId 
             where q.BrodcastType == QuestionBrodcastType.All || filterQuestionInfo.ToProfileId == qr.ToProfileId 
             select q);
}

// second if condition to inject AND query and i want to this be OR injection
if (filterQuestionInfo.ProfileId.HasValue)
{
    query = (from q in query 
             where q.ProfileId == filterQuestionInfo.ProfileId 
             select q);
}

现在我想创建" OR"注入,当我调用.ToList()时,我只看到我需要的SQL查询。在顶部示例中,如果ToProfileIdProfileId具有值,则会在" ProfileId"中找到发送到ToProfileId值的问题和来自个人资料ID的0个问题。值因为第二个查询是"而且"条件到第一次查询。但是当我填写两个值时,我想要它们两个。

  1. 当两个值为空时:我过滤了所有问题(现在可以使用)

  2. 当ToProfileId或ProfileId的一个值为null时:我过滤了关于该值的所有问题都不为null(现在可以使用)

  3. 当两个值都填满时,我想要两个问题列表(现在不起作用)

  4. 注意:我不想创建一个查询并将所有条件注入该查询。

1 个答案:

答案 0 :(得分:0)

假设QuestionRelationsInfoesQuestionInfoes作为名为QuestionRelationsInfoes的导航属性存在,那么您不需要join

不幸的是,您必须根据3个场景构建查询(两个过滤器集,仅第一个过滤器集,仅第二个过滤器集)。

var query = context.QuestionInfoes.Include(x => x.RelationsInfoes);

if (filterQuestionInfo.ToProfileId.HasValue && filterQuestionInfo.ProfileId.HasValue)
{
    query = query.Where(q =>
        q.BrodcastType == QuestionBrodcastType.All ||
        q.QuestionRelationsInfoes.ToProfileId == filterQuestionInfo.ToProfileId ||
        q.ProfileId == filterQuestionInfo.ProfileId);
}
else if (filterQuestionInfo.ToProfileId.HasValue)
{
    query = query.Where(q => q.BrodcastType == QuestionBrodcastType.All || filterQuestionInfo.ToProfileId == q.QuestionRelationsInfoes.ToProfileId);
}
else if (filterQuestionInfo.ProfileId.HasValue)
{
    query = query.Where(q.ProfileId == filterQuestionInfo.ProfileId);
}

作为替代方案,如果您不喜欢代码重复,可以通过首先检查过滤器是否为空来将检查推送到SQL:

var query = context.QuestionInfoes.Include(x => x.RelationsInfoes);

if (filterQuestionInfo.ToProfileId.HasValue || filterQuestionInfo.ProfileId.HasValue)
{
    query = query.Where(q =>
        (filterQuestionInfo.ToProfileId.HasValue && (q.BrodcastType == QuestionBrodcastType.All || filterQuestionInfo.ToProfileId == q.QuestionRelationsInfoes.ToProfileId)) ||
        (filterQuestionInfo.ProfileId.HasValue && q.ProfileId == filterQuestionInfo.ProfileId));
}