【问题标题】:Mysql Find free time slots between appointmentsMysql查找约会之间的空闲时间段
【发布时间】:2013-11-20 14:47:03
【问题描述】:

我正在尝试查找一天的空闲时间段,但我被困在正确的查询上。 开放时间或一天在每天 9:00 到 22:00 之间运行 以下查询返回全天的正确数据,除非当天的第一个预订是在 10:00,它不会返回 9 点之间的未预订时段:00 和 10:00,或者如果在 21:30 到 21:40 期间预订,则不会显示当天的最后一个时段是空闲的。

在为每一天和 set_id 解决这个问题时,我必须创建一个以 id=1 和 id=6 表示的一天开始和一天结束的 1 分钟条目。

我试图避免为每天和每个 set_id 创建这两个插入

CREATE TABLE bookings
(`id` int, `time_from` datetime, `time_to` datetime, `set_id` int);


INSERT INTO bookings
    (`id`, `time_from`, `time_to`, `set_id`)
VALUES
    (1, '2013-11-20 08:59:00', '2013-11-20 09:00:00', 6),
    (2, '2013-11-20 09:10:00', '2013-11-20 10:00:00', 6),
    (3, '2013-11-20 11:10:00', '2013-11-20 11:30:00', 6),
    (4, '2013-11-20 12:00:00', '2013-11-20 12:40:00', 6),
    (5, '2013-11-20 16:20:00', '2013-11-20 16:50:00', 6),
    (6, '2013-11-20 22:00:00', '2013-11-20 22:01:00', 6)
;

SELECT Available_from, Available_to
FROM (
    SELECT @lasttime_to AS Available_from, time_from AS Available_to, @lasttime_to := time_to
    FROM (SELECT time_from, time_to
          FROM bookings
          WHERE set_id = 6
            AND time_to >= '2013-11-20 08:59'
            AND time_from < '2013-11-20 22:01'
      ORDER BY time_from) e
    JOIN (SELECT @lasttime_to := NULL) init) x
WHERE Available_to > DATE_ADD(Available_from, INTERVAL 9 MINUTE);


|      AVAILABLE_FROM |                    AVAILABLE_TO |
|---------------------|---------------------------------|
| 2013-11-20 09:00:00 | November, 20 2013 09:10:00+0000 |
| 2013-11-20 10:00:00 | November, 20 2013 11:10:00+0000 |
| 2013-11-20 11:30:00 | November, 20 2013 12:00:00+0000 |
| 2013-11-20 12:40:00 | November, 20 2013 16:20:00+0000 |
| 2013-11-20 16:50:00 | November, 20 2013 22:00:00+0000 |

任何帮助将不胜感激。

http://www.sqlfiddle.com/#!2/b30a0/2

    CREATE TABLE `days` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `date` date NOT NULL,
  `time_from` datetime NOT NULL,
  `time_to` datetime NOT NULL,
  `step` int(11) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8;


INSERT INTO `days` (`id`, `date`, `time_from`, `time_to`, `step`)
VALUES
    (1, '2013-11-20', '2013-11-20 09:00:00', '2013-11-20 22:00:00', 10),
    (2, '2013-11-21', '2013-11-21 09:00:00', '2013-11-21 22:00:00', 10);

再靠近一点!

INSERT INTO `bookings` (`id`, `date`, `time_from`, `time_to`, `set_id`, `name`, `email`, `telephone`, `amount`, `notes`, `is_paid`, `is_booked`)
VALUES
    (25, '2013-11-20', '2013-11-20 09:10:00', '2013-11-20 09:30:00', 1, '', '', '', NULL, NULL, 0, 0),
    (26, '2013-11-20', '2013-11-20 10:30:00', '2013-11-20 11:30:00', 1, '', '', '', NULL, NULL, 0, 0),
    (27, '2013-11-20', '2013-11-20 12:30:00', '2013-11-20 13:20:00', 1, '', '', '', NULL, NULL, 0, 0),
    (29, '2013-11-20', '2013-11-20 15:00:00', '2013-11-20 16:40:00', 1, '', '', '', NULL, NULL, 0, 0);

这就是我得到的

availableFrom         availableTo
9:00                  2013-11-20 09:10:00
2013-11-20 09:30:00       2013-11-20 10:30:00
2013-11-20 11:30:00       2013-11-20 12:30:00
9:00                  2013-11-20 15:00:00
2013-11-20 15:00:00       22:00

【问题讨论】:

  • 感谢您的回复 我在哪里需要工会?
  • 我确实有一个日期表,其中包含 id、日期、time_from、time_to、step
  • so id= 1, date= 2013-11-20, time_from= 2013-11-20 09:00:00, time_to= 2013-11-20, step= 10
  • 该表现已添加到问题中!
  • 我正在使用的 1 分钟时段,因此我可以在 9:00 到 10:00 之间获得空时段

标签: mysql


【解决方案1】:

一种可能的选择是将表格与自身进行左连接:

select (case when ltime_to is null then '9:00' else ltime_to end) as availableFrom,
rtime_from as availableTo
from (select l.time_to as ltime_to, r.time_from as rtime_from from bookings r 
left join bookings l on l.id=r.id-1) lr
union
select max(time_from) as availableFrom, '22:00' as availableTo from bookings

【讨论】:

  • 不这样轮回什么都没有。
  • 啊,我明白了,没有立即明白你在做什么。一种简单而愚蠢的方法是插入一个在一天的第一时刻开始和停止的虚假预订,然后您可以将其用作 first time_from。其他选项,如果您保证您的表具有不重叠的连续期间,可以在 l.id=r.id-1 上将表与自身进行 LEFT JOIN,然后使用之前的 time_from 或一天的开始作为 time_from。
  • 谢谢,伪造的条目是上面插入的第一个和最后一个条目 - id 的 1 和 6 你会注意到它们只有 1 分钟的预订。这就是我想要摆脱的,因为我必须每天为 6 个场地或 set_id 创建那些虚假预订。并认为必须有一种方法可以将开始和结束时间集成到查询中,这样我就不必进行虚假插入。 (我喜欢这个名字是假的!)我可以使用日期表中的开始和结束时间吗?谢谢
  • 另一个选项怎么样 - 将该表与自身左连接,但向后移动一行?
  • 我不确定我是否跟着你?
猜你喜欢
  • 1970-01-01
  • 2022-06-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-08-06
  • 2018-12-13
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多