Database
 sql >> Baza danych >  >> RDS >> Database

Jak obliczyć różnicę między dwoma datami w T-SQL

Problem:

Masz dwie kolumny typu datetime i chcesz obliczyć różnicę między nimi.

Przykład:

W travel tabeli, są trzy kolumny:id , departure i arrival . Chcesz obliczyć różnicę między arrival i departure .

travel tabela wygląda tak:

id wyjazd przybycie
1 2018-03-25 12:00:00 2018-04-05 07:30:00
2 2019-09-12 15:50:00 23-10-2019 10:30:30
3 2018-07-14 16:15:00 2018-07-14 20:40:30
4 2018-01-05 08:35:00 2019-01-08 14:00:00

Rozwiązanie 1 (różnica w sekundach):

SELECT
  id,
  departure,
  arrival,
  DATEDIFF(second, departure, arrival) AS difference
FROM travel;

Wynik:

id wyjazd przybycie różnica
1 2018-03-25 12:00:00 2018-04-05 07:30:00 934200
2 2019-09-12 15:50:00 23-10-2019 10:30:30 3523230
3 2018-07-14 16:15:00 2018-07-14 20:40:30 15930
4 2018-01-05 08:35:00 2019-01-08 14:00:00 31814700

Dyskusja:

Aby obliczyć różnicę między arrival i odejście w T-SQL, użyj DATEDIFF(datepart, startdate, enddate) funkcjonować. datepart argument może być microsecond , second , minute , hour , day , week , month , quarter lub year . Tutaj chcesz uzyskać różnicę w ciągu kilku sekund, więc wybierz drugą. Aby uzyskać różnicę w godzinach, wybierz hour; dla różnicy w miesiącach wybierz month itp. startdate i enddate argumentami są początek i koniec datetime odpowiednio kolumny (tutaj, departure i arrival , odpowiednio).

Rozwiązanie 2 (różnica w dniach, godzinach, minutach i sekundach):

WITH difference_in_seconds AS (
  SELECT
    id,
    departure,
    arrival,
    DATEDIFF(SECOND, departure, arrival) AS seconds
  FROM travel
),

differences AS (
  SELECT
    id,
    departure,
    arrival,
    seconds,
    seconds % 60 AS seconds_part,
    seconds % 3600 AS minutes_part,
    seconds % (3600 * 24) AS hours_part
  FROM difference_in_seconds
)

SELECT
  id,
  departure,
  arrival,
  CONCAT(
    FLOOR(seconds / 3600 / 24), ' days ',
    FLOOR(hours_part / 3600), ' hours ',
    FLOOR(minutes_part / 60), ' minutes ',
    seconds_part, ' seconds'
  ) AS difference
FROM differences;

Wynik:

id wyjazd przybycie różnica
1 2018-03-25 12:00:00 2018-04-05 07:30:00 10 dni 19 godzin 30 minut 0 sekund
2 2019-09-12 15:50:00 23-10-2019 10:30:30 40 dni 18 godzin 40 minut 30 sekund
3 2018-07-14 16:15:00 2018-07-14 20:40:30 0 dni 4 godziny 25 minut 30 sekund
4 2018-01-05 08:35:00 2019-01-08 14:00:00 368 dni 5 godzin 25 minut 0 sekund

Dyskusja:

Najpierw oblicz różnicę między arrival i departure w kilka sekund, używając DATEDIFF() funkcja (pierwsze CTE o nazwie difference_in_seconds ), podobnie jak w Rozwiązaniu 1. Następnie oblicz, ile sekund jest powyżej pełnych minut (seconds_part ) do późniejszego obliczenia sekund, ile sekund przekracza pełne godziny (minutes_part ) do późniejszego obliczenia minut i liczby sekund przekraczających pełne godziny (hours_part ) do wykorzystania później do obliczenia godzin.

Aby to zrobić, użyj operatora %. Na przykład godzina ma 3600 sekund, więc aby dowiedzieć się, ile sekund jest w minutes_part , znajdź resztę z dzielenia przez 3600 w ten sposób:

seconds % 3600 AS minutes_part

Podobnie jest 3600 * 24 sekund dziennie, aby obliczyć, ile sekund jest w hours_part , napisz:

seconds % (3600 * 24) AS hours_part

Po obliczeniu tych reszt (w drugim CTE, nazwanym differences ), możesz wreszcie uzyskać różnicę w dniach, godzinach, minutach i sekundach. Aby uzyskać liczbę sekund, minut, godzin i dni, podziel liczbę sekund w pozostałej części przez odpowiednią liczbę sekund w dniach, godzinach lub minutach. Na przykład, aby dowiedzieć się, ile minut powinno być wyświetlane, weź minutes_part i podziel go przez 60, ponieważ w ciągu godziny jest 60 minut. Potrzebujesz tylko części całkowitej z tego (tzn. bez części dziesiętnej), więc użyj FLOOR() działać tak:

FLOOR(minutes_part / 60)

Na koniec wystarczy wyświetlić w jednym ciągu to, co obliczyłeś. Aby to zrobić, użyj CONCAT() funkcja w zewnętrznym zapytaniu:

CONCAT(
    FLOOR(seconds / 3600 / 24), ' days ',
    FLOOR(hours_part / 3600), ' hours ',
    FLOOR(minutes_part / 60), ' minutes ',
    seconds_part, ' seconds'
  ) AS difference

Przedstawione tutaj rozwiązanie zwraca datetime różnica jako tekst. Możesz łatwo zmodyfikować rozwiązanie, aby uzyskać tylko liczby bez tekstu. Możesz także przechowywać dni, godziny, minuty i sekundy w różnych kolumnach:

FLOOR(seconds / 3600 / 24) AS days,
FLOOR(hours_part / 3600) AS hours,
FLOOR(minutes_part / 60) AS minutes,
seconds_part AS seconds

  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Diagramy ER w IRI Workbench

  2. Problemy z konfiguracją dziennika transakcji

  3. Specjalne wyspy

  4. Jak zmienić nazwę tabeli w SQL?

  5. Opcje dostrajania wydajności bazy danych SQL Azure