Проверка, равно ли время времени с длительностью

#php #mysql #mysqli #time #pdo

#php #mysql #mysqli #время #pdo

Вопрос:

Итак, я создаю систему доставки еды. Я хочу проверить, занято ли время. Проблема в том, что существует длительность, связанная с некоторым временем. Это довольно легко сделать, если длительности нет.

ПРИМЕР РАБОЧЕГО КОДА:

Например, вот моя deliveries таблица:

  ---- --------------- --------------- ---------- 
| id | delivery_date | delivery_time | duration |
 ---- --------------- --------------- ---------- 
| 1  | 2018-02-18    | 10:30:00      | null     |
 ---- --------------- --------------- ---------- 
 

Допустим, мое выбранное время доставки равно 2018-02-18 10:30:00 , тогда оно будет принято. Код:

 $deliveryDate = '2018-02-18';
$deliveryTime = '10:30:00';

$stmt = "SELECT id FROM deliveries WHERE appointment_date = :date AND appointment_time = :time";
$stmt->bindParam(':date', $deliveryDate);
$stmt->bindParam(':time', $deliveryTime);
$stmt->execute();
$result = $stmt->fetch();

if($result) {
    echo 'Sorry, this is already taken!';
}
 

Этот код работает.


НЕ РАБОЧИЙ ПРИМЕР КОДА:

Я пытаюсь выяснить, если я изменю значение duration с null на 40 (40 минут), его нужно будет заблокировать 2018-02-18 10:30:00 to 11:10:00 .

Допустим, длительность равна 40 (минутам) и delivery_time равна 11:05:00 . Он должен блокировать его.

  ---- --------------- --------------- ---------- 
| id | delivery_date | delivery_time | duration |
 ---- --------------- --------------- ---------- 
| 1  | 2018-02-18    | 10:30:00      | 40       |
 ---- --------------- --------------- ---------- 

$deliveryDate = '2018-02-18';
$deliveryTime = '11:05:00';

$stmt = "SELECT id FROM deliveries WHERE appointment_date = :date AND appointment_time = :time";
$stmt->bindParam(':date', $deliveryDate);
$stmt->bindParam(':time', $deliveryTime);
$stmt->execute();
$result = $stmt->fetch();

if($result) {
    echo 'Sorry, this is already taken!';
}
 

Как я могу заставить его учитывать продолжительность?

Комментарии:

1. Что вы пробовали до сих пор? Кажется простым случаем установки минимального ( delivery_time ) и максимального (плюс duration ) времени.

Ответ №1:

Если вы объедините столбец даты и времени в a datetime , вы можете использовать timestampadd() его для добавления продолжительности, а затем проверить, находятся ли заданные дата и время в периоде.

 SELECT id
       FROM deliveries
       WHERE cast(concat(delivery_date, ' ', delivery_time) AS datetime) <= cast(concat(:date, ' ', :time) AS datetime)
             AND timestampadd(minute, duration, cast(concat(delivery_date, ' ', delivery_time) AS datetime)) > cast(concat(:date, ' ', :time) AS datetime);
 

db<>скрипка

Вы могли бы облегчить себе жизнь, если бы просто использовали datetime здесь два s вместо того, чтобы разбивать его на три столбца. Тогда вы также можете воспользоваться индексами.

Комментарии:

1. Потеря возможности использовать индексы (если они, конечно, есть) может иметь огромное значение с точки зрения производительности.