LINQ Where子句内联循环?

时间:2015-04-28 16:13:09

标签: c# linq entity-framework linq-to-entities where-clause

我有一个名为start和length的数据库值。

start是预订的开始时间(1-> 09:00,2-> 10:00等),长度是以小时为单位的长度。

然后,我有一系列的开始时间和结束时间。我希望能够检查每个开始和结束对是否已经预订。到目前为止,我认为如果开始时间相同,则预订,或者如果结束时间相同,则也会预订。但是如果开始和结束时间介于比较时间之间,它将返回未预订,这是错误的。

我正在尝试编写LINQ查询来测试预订是否已存在于数据库中。到目前为止我已经

var proposedRequest = db.requests.Include(r => r.rooms);
proposedRequest = proposedRequest.Where(r => r.booked.Equals(1));
proposedRequest = proposedRequest.Where(r => r.roundID.Equals(roundID));
proposedRequest = proposedRequest.Where(r => r.day.Equals(day));

int[] startTimes = new int[length];
int[] endTimes = new int[length];
for(var q=0;q<length;q++)
{
    startTimes[q] = time + q;
    endTimes[q] = time + q + 1;
}
proposedRequest = proposedRequest.Where(s => startTimes.Contains(s.start) || endTimes.Contains(s.start+s.length));

现在,这仅适用于新预订与数据库中已有的预订同时开始,或者同时结束的情况。这不会考虑以下情况

db中有一条记录,其中start - &gt; 2和长度 - > 3。

因此预订时间为10:00-> 13:00。

但是我说这是针对一个从11:00开始并在12结束的条目进行检查。由于开始和结束时间不匹配,它不会像预订那样回来。

解决这个问题的最佳方法是什么?

我认为合适的唯一方法是遍历我的startTime和endTime数组,并为每对产生另一个子句,产生类似如下的内容:

.Where((s => s.startTime<startTime[i] && (s.startTime + s.Length) > endTime[i]) || (s => s.startTime<startTime[i+1] && (s.startTime + s.Length) > endTime[i+1]))

但我不认为这是可能的。

2 个答案:

答案 0 :(得分:4)

根据this回答,如果(StartA <= EndB) and (EndA >= StartB)

,则会有两个范围重叠

在你的情况下:

StartA = s.start
EndA = s.start + s.length
StartB = time
EndB = time + length

所以你的最后一个条件应该是这样的:

proposedRequest = proposedRequest.Where(s => s.start <= time + length &&
                                             s.start + s.length >= time);

答案 1 :(得分:1)

这将返回具有StartTime,EndTime和布尔值的对象,该布尔值表示它是否已经预订。

var proposedRequest = db.requests
    .Include(r => r.rooms)
    .Where(r => r.booked.Equals(1))
    .Where(r => r.roundID.Equals(roundID))
    .Where(r => r.day.Equals(day))
    .ToList();

//int[] startTimes = new int[length];
//int[] endTimes = new int[length];
//for(var q=0;q<length;q++)
//{
//    startTimes[q] = time + q;
//    endTimes[q] = time + q + 1;
//}
var times=Enumerable
   .Range(time,length)
   .Select(r=>
       new {
           StartTime=r,
           EndTime=r+1,
           Booked=proposedRequest.Any(pr=>pr.StartTime<=r && pr.StartTime+pr.Length>r)
           }).ToList();