根据List<>过滤来自数据库的项目

时间:2015-10-05 03:02:52

标签: c# linq

我有一个接受两个List<int>的方法,我需要根据List<>从数据库中获取数据。

所以,我收到了一个List<PersonId>List<NationalityId>,我需要获得一个记录与PersonIdsNationalistId匹配的结果集。

public List<PersonDTO> SearchPeople(List<int> persons, Lisy<int> nationalities)
{
  var results = (from c in myDbContect.People where .... select c).ToList();
}

请注意,我认为列表可能为空。

有效率吗? 我打算试试:

where ((persons != null && persons.Count > 0) && persons persons.Contains(x=>x.PersonId))

但是这会产生相当低效的SQL,并且当我添加更多搜索参数时,linq可能会变得非常混乱。

有没有一种有效的方法来实现这一目标?

连接方法可能很容易阅读,但我面临的问题是,如果输入列表为空,则不应过滤。也就是说,如果国籍是空的,请不要过滤掉:

    var results = (from c in entities.Persons
                   join p in persons on c.PersonId equals b
                   join n in nationalities on c.NationalityId equals n

等于n                        选择c).ToList();

如果任何列表为空,则不会返回任何结果。哪个,不好。

2 个答案:

答案 0 :(得分:1)

如果您加入IQueryable IEnumerable(在这种情况下,entities.Personspersons),您的过滤将不会在您的查询中进行。而是枚举IQueryable,从数据库中检索所有记录,而使用IEnumerable连接方法在内存中执行连接。

要对查询中的列表执行过滤,有两个主要选项:

  1. 双方使用IQueryable加入。如果您的id列表来自另一个查询的执行,这可能是可能的,在这种情况下,您可以在连接中使用基础查询而不是生成的一组ID。

  2. 对列表使用contains运算符。这仅适用于小型列表,因为每个附加ID都需要自己的查询参数。如果您有许多ID,则可以通过批处理扩展此方法。

  3. 如果要在列表为空时跳过过滤,则可以考虑使用扩展方法调用而不是LINQ语法。这允许您使用if语句:

    IQueryable<Person> persons = entities.persons;
    List<int> personIds = new List<int>();
    if(personIds.Count > 0)
    {
        persons = persons.Where(p => personIds.Contains(p.PersonId));
    }
    var results = persons.ToList();
    

    请注意,Where谓词使用上面的选项#2,仅在集合中有任何ID时才会应用。

答案 1 :(得分:0)

如果您想获取人员的所有记录,例如,如果列表为空,然后按照nationalityId列表过滤,如果它不为空,您可以执行以下操作:

$.ajax({
                     type: "POST",
                     url: "A2_JVV.aspx/ds2json",
                     contentType: "application/json; charset=utf-8",
                     dataType: "json",
                     success: function (msg) {
                         var result = $.JSON(msg);
                         $("#Result").text(result.d);
                     }

                 });