复杂的DTO和LINQ

时间:2013-06-15 20:42:02

标签: c# linq

class PeopleDTO
{
    string Name { get; set; }
    List<AwardDTO> Awards { get; set; }
}


class AwardDTO
{
    int AwardID {get; set; }
    string AwardName {get; set; }
}

我正在尝试使用LINQ过滤我的People对象,以获得“AwardID”等于5的任何人。我尝试过以下但我没有得到它:

List<PeopleDTO> people = GetPeople();
var test = (from p in people.Where(a => a.Awards.Where(a => a.AwardID == 5)) select p).ToList();

有什么建议吗?

4 个答案:

答案 0 :(得分:2)

people.Where(p=>p.Awards.Any(a=>a.AwardId == 5)).ToList()

答案 1 :(得分:0)

您只需要进行一项小改动:

List<PeopleDTO> people = GetPeople();
var test = (from p in people.Where(a => a.Awards.Any(a => a.AwardID == 5)) select p).ToList();

答案 2 :(得分:0)

var test = people.Where(l => l.Awards.Any(a => a.AwardId == 5));

会做..那只是查询部分,你可能想要执行它。

答案 3 :(得分:0)

问题是Where返回匹配元素 sequence ,因此生成的类型错误。这是根本问题:

// Wrong (type error)
from p in people
  .Where(
     // Results in type error as result of Where is Enumerable, not bool.
     // The lambda signature is People => Enumerable[Award] which is
     // incompatible with People => bool required for the outer Where.
     a => a.Awards.Where(a => a.AwardID == 5)
  )
select p

// Working - but NOT ideal as it forces materialization of the
// matching award count! However, types are correct.
from p in people
  .Where(
     // Now we get a lambda: People => bool
     a => a.Awards.Where(a => a.AwardID == 5).Count() > 0
  )
select p

Where(f).Count() > 0 Any(f)更理想的解决方案,正如其他答案中所讨论的那样。除了更清楚之外,Any通常也是有利的,因为它不需要首先实现序列 - 毕竟,每个源元素都可以匹配。

Where的实际结果将是IEnumerable[X]IQueryable[X],具体取决于应用它的来源。重点是,单独存在会导致不兼容的值,从而导致输入错误的lambda。