我有2个MySQL表,'scheduled_time'和'约会'
'scheduled_time'有2个DateTime字段,'start'和'end' - 这是我可以进行约会的时间范围。
'约会'包含约会详情,但也包含'开始'和'结束'字段,这最终将在'scheduled_time'中指定的范围内。
在考虑两个表时,找到空时间块的最佳方法是什么?
假设我从2010年11月9日上午8点到下午2点开始'scheduled_time'。我有一个'预约'从早上8点到早上10点,一个从下午1点到下午2点。我怎样才能找到下一个可用的1小时块?
答案 0 :(得分:3)
我刚才这样做了。我们有类似的结构:
我所做的基本上是这个(步骤):
答案 1 :(得分:0)
首先,创建一个number table。这里的例子名为“Numbers”,列号为“number”。
然后你可以做类似
的事情select chour as [Free Hour] from Numbers n
inner join Scheduled s on n.chour >= s.start and n.chour < s.[end]
where chour not in
(
select chour from Numbers n
inner join Appointments a ON n.chour >= q.start and n.chour < a.[end]
)
数字是我的Numbers表, chour 是一个定义为
的计算列DATE_ADD('2010-11-08', INTERVAL number HOUR)
当然,您也可以将其存储为持久列。
很抱歉,如果语法不完全正确,我会正常进行T-SQL: - )
编辑:这种技术仅适用于固定的时间块(小时只是一个例子,你可以轻松地做半小时),但在这种情况下它非常有效和可读。业务中的一个常见应用是映射日期,因为这是大多数合同所在的粒度,您可以使用少量表来覆盖很多天。
答案 2 :(得分:0)
这是一个使用虚拟整数表的好地方,它可以帮助你create data from nothing。这是一个例子:
create table ints(i tinyint);
insert into ints values(0),(1),(2),(3),(4),(5),(6),(7),(8),(9);
然后,您可以使用此表的几个交叉连接来生成由scheduled_time表表示的一小时长的窗口表,并将结果与约会表连接,以查找没有已安排的内容的窗口。 / p>
SELECT
h.HourWindowStart, h.HourWindowEnd
FROM (
SELECT
s.start + INTERVAL t.i*100 + u.i*10 + v.i HOUR AS HourWindowStart,
s.start + INTERVAL t.i*100 + u.i*10 + v.i + 1 HOUR AS HourWindowEnd
FROM scheduled_time s
JOIN ints AS t
JOIN ints AS u
JOIN ints AS v
WHERE s.start + INTERVAL t.i*100 + u.i*10 + v.i HOUR < s.end
ORDER BY HourWindowStart
) as h
LEFT JOIN appointments a ON a.end > h.HourWindowStart AND a.start < h.HourWindowEnd
WHERE a.start IS NULL
您可以调整此过程的各个部分来计算更大/更小的可用性窗口(按半小时,按天等),根据可用性窗口的最大数量使用整数表的更多或更少的交叉连接可以在scheduled_time中的单个开始/结束范围中表示,预先创建日期日历并连接两个表等。