SQLinfo.ru - Все о MySQL

Форум пользователей MySQL

Задавайте вопросы, мы ответим

Вы не зашли.

#1 08.06.2010 01:13:10

vasya
Архат
MySQL Authorized Developer
Откуда: Орел
Зарегистрирован: 07.03.2007
Сообщений: 5842

Проектирвание бд - учет времени

Задача такова.
У каждого мастера свой график работы (периодически меняющийся). Им даются заказы на время выполнения которых мастер считается занятым. Нужно выбрать мастеров свободных в определенный промежуток времени, причем величина свободного окна должна быть не менее чем х (например, найти тех кто свободен с 8 до 13 такого-то числа и свободное окно не менее полутора часов).

Я предполагаю использовать следующую таблицу:

CREATE TABLE `raspisanie` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `master_id` int(11) NOT NULL,
  `exact_date` date DEFAULT NULL,
  `day_of_week` tinyint(4) DEFAULT NULL,
  `time_from` time DEFAULT NULL,
  `time_to` time DEFAULT NULL,
  `is_on` tinyint(4) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8

Если заполнено поле exact_date, то запись относится к конкретной дате; если day_of_week, то ко дню недели. Поле is_on принимает значения 1 или 0 (свободен/занят).
Такая структура позволяет задать каждому произвольный график работы (во вторник до обеда, в четверг весь день, а в пятницу шабат) (у этих записей is_on = 1). И потом заносится время выполнения конкретного заказа (is_on = 0).

Чтобы найти тех кто свободен с 8 до 13 такого-то числа и свободное окно не менее полутора часов, мы сначала смотрим работает ли в это время мастер, и, если да, то проверяем на перекрытие записями с is_on = 0 для этой даты. Если перекрывается, то проверяем на длительность и последующие перекрытия каждый из получившихся свободных промежутков.

Вопрос в том, правильный ли это подход или есть более удобный способ?

Неактивен

 

#2 08.06.2010 01:29:15

vasya
Архат
MySQL Authorized Developer
Откуда: Орел
Зарегистрирован: 07.03.2007
Сообщений: 5842

Re: Проектирвание бд - учет времени

Стоило написать о проблеме и появилось понимание. Мне не нравиться, что в предложенном способе нельзя получить ответ одним простым запросом.

Как вариант, еженочно генерировать таблицу на определенный срок (например месяц), где будут указаны только свободные промежутки. Т.е. если мастер работает 15.06.2010 с 8 до 19 с перерывом на обде с 13 до 14, то в таблице будут две записи на этот день с 8 до 13 и с 14 до 19. При получении заказа с 10 до 12, запись с 8 до 13 замениться на две с 8 до 10 и с 12 до 13.
Тогда исходная задача решается одним простым запросом к базе.

Есть ли предел совершенству или есть ещё более простое решение?

Неактивен

 

#3 08.06.2010 13:54:42

paulus
Администратор
MySQL Authorized Developer and DBA
Зарегистрирован: 22.01.2007
Сообщений: 6757

Re: Проектирвание бд - учет времени

Наличие day_of_week эффективно сводит задачу к многозапросной. Или нужно
прегенерить реальное расписание, или считать для каждой строки (и тем самым
убить возможность использовать индексы).

Без day_of_week задача сводится к «все мастера, кроме занятых в это время».
А «занятый» — это time_from < 8 and time_to > 13. Ну то есть LEFT JOIN таблицы
мастеров с расписанием с вот этим дополнительным условием.

Неактивен

 

Board footer

Работает на PunBB
© Copyright 2002–2008 Rickard Andersson