添加where子句到嵌套Linq选择

时间:2010-06-30 14:23:49

标签: c# linq

我还是Linq的新手,所以如果你看到我真的不应该做的事情,请随时建议改变。

我正在制定一个新系统,允许警官报名加班。部分数据显示在地图上,搜索条件可过滤不需要的位置。为了使数据更易于使用,使用Linq将其读入层次结构对象结构。在此示例中,作业可以包含多个班次,每个班次可以有多个职位可用。阅读它们的Linq语句如下所示。

        var jobs = (from j in db.Job
                    join s in db.Shift on j.Id equals s.JobId into shifts
                    select new JobSearchResult
                    {
                        JobNumber = j.Id,
                        Name = j.JobName,
                        Latitude = j.LocationLatitude,
                        Longitude = j.LocationLongitude,
                        Address = j.AddressLine1,
                        Shifts = (from shift in shifts
                                  join p in db.Position on shift.Id equals p.ShiftId into positions
                                  select new ShiftSearchResult
                                  {
                                      Id = shift.Id,
                                      Title = shift.ShiftTitle,
                                      StartTime = shift.StartTime,
                                      EndTime = shift.EndTime,
                                      Positions = (from position in positions
                                                   select new PositionSearchResult
                                                   {
                                                       Id = position.Id,
                                                       Status = position.Status
                                                   }).ToList()
                                  }).ToList()
                    });

工作正常并经过测试。可能有更好的方法来做到这一点,如果你知道一种方式,请随时提出建议。我的问题是这个。创建查询后,将添加搜索条件。我知道我可以在创建查询时添加它但是为此之后更容易实现。现在,我可以轻松添加看起来像这样的标准。

jobs = jobs.Where(j => j.JobNumber == 1234);

然而,我无法弄清楚如何为班次或职位做同样的事情。换句话说,我怎么能在特定时间之后添加一个班次开始的条件呢?以下示例是我想要完成的但不会(显然)工作。

jobs = jobs.Shifts.Where(s = s.StartTime > JobSearch.StartTime)      //JobSearch.StartTime is a form variable.

有人有任何建议吗?

1 个答案:

答案 0 :(得分:1)

步骤1:创建关联,以便可以将连接隐藏在EntitySet属性后面。 http://msdn.microsoft.com/en-us/library/bb629295.aspx

第2步:构建过滤器。您有3个可查询和过滤器交互的可能性。首先指定最里面的过滤器,以便外部过滤器可以使用它们。

以下是所有工作(未经过滤)。每项工作只有3个空缺职位。每个班次都有这些空缺职位。

Expression<Func<Position, bool>> PositionFilterExpression =
  p => p.Status == "Open";

Expression<Func<Shift, bool>> ShiftFilterExpression =
  s => s.Positions.Where(PositionFilterExpression).Count == 3  

Expression<Func<Job, bool>> JobFilterExpression =
  j => true

第3步:把它们放在一起:

   List<JobSearchResult> jobs = db.Jobs
     .Where(JobFilterExpression)
     .Select(j => new JobSearchResult
     { 
       JobNumber = j.Id, 
       Name = j.JobName, 
       Latitude = j.LocationLatitude, 
       Longitude = j.LocationLongitude, 
       Address = j.AddressLine1, 
       Shifts = j.Shifts
         .Where(ShiftFilterExpression)
         .Select(s => new ShiftSearchResult
         {
           Id = s.Id,
           Title = s.ShiftTitle,
           StartTime = s.StartTime,
           EndTime = s.EndTime,
           Positions = s.Positions
             .Where(PositionFilterExpression)
             .Select(p => new PositionSearchResult
             {
               Id = position.Id,
               Status = position.Status
             })
             .ToList() 
         })
         .ToList()
     })
     .ToList();