Pytanie Data MYSQL Czas do najbliższej godziny


Mam pole daty w bazie danych MySQL i chcę wyprowadzić wynik do najbliższej godziny.

na przykład 2012-04-01 00:00:01 powinien przeczytać 2012-04-01 00:00:00


30
2018-03-13 07:49


pochodzenie


możliwy duplikat Jak zaokrąglić DateTime w MySQL? - Makoto


Odpowiedzi:


Aktualizacja: myślę https://stackoverflow.com/a/21330407/480943 jest lepszą odpowiedzią.


Możesz to zrobić z pewną arytmetyczną datą:

SELECT some_columns,
    DATE_ADD(
        DATE_FORMAT(the_date, "%Y-%m-%d %H:00:00"),
        INTERVAL IF(MINUTE(the_date) < 30, 0, 1) HOUR
    ) AS the_rounded_date
FROM your_table

Objaśnienia:

  • FORMAT DATY: DATE_FORMAT(the_date, "%Y-%m-%d %H:00:00") zwraca datę skróconą do najbliższej godziny (ustawia minutę i drugą część na zero).

  • MINUTA: MINUTE(the_date) pobiera minutową wartość daty.

  • GDYBY: Jest to warunkowe; jeśli wartość w parametrze 1 jest prawdziwa, to zwraca parametr 2, w przeciwnym razie zwraca parametr 3. So IF(MINUTE(the_date) < 30, 0, 1) oznacza "Jeśli wartość minutowa jest mniejsza niż 30, zwróć 0, w przeciwnym razie zwróć 1". Właśnie tego użyjemy do zaokrąglenia - jest to liczba godzin, którą można ponownie dodać.

  • DATE_ADD: To dodaje liczbę godzin do rundy do wyniku.


36
2018-03-13 07:59





Pół godziny to 30 minut. Po prostu dodaj 30 minut do znacznika czasu i skróć minuty i sekundy.

SELECT DATE_FORMAT(DATE_ADD(timestamp_column, INTERVAL 30 MINUTE),'%Y-%m-%d %H:00:00') FROM table


23
2018-01-24 10:35





pierwsze rozwiązanie duszy obcina zamiast zaokrąglać, a drugie rozwiązanie nie działa z przypadkami oszczędzania w świetle dziennym, takimi jak:

select FROM_UNIXTIME(UNIX_TIMESTAMP('2012-03-11 2:14:00') - MOD(UNIX_TIMESTAMP('2012-03-11 2:14:00'),300));

Oto alternatywna metoda (1):

DATE_ADD(
    tick,
    INTERVAL (IF((MINUTE(tick)*60)+SECOND(tick) < 1800, 0, 3600) - (MINUTE(tick)*60)+SECOND(tick)) SECOND
)

Jeśli nie musisz martwić się o sekundy, możesz uprościć to w ten sposób (2):

DATE_ADD(
    tick,
    INTERVAL (IF(MINUTE(tick) < 30, 0, 60) - MINUTE(tick)) MINUTE
)

Lub jeśli wolisz skracać zamiast rundy, tutaj jest prostsza wersja metody duszy (3):

DATE_SUB(tick, INTERVAL MINUTE(tick)*60+SECOND(tick) SECOND)

EDYCJA: Profilowałem niektóre z tych zapytań na moim komputerze lokalnym i stwierdziłem, że dla 100 000 wierszy średni czas był następujący:

  • dusze UNIXTIME metoda: 0,0423 ms (szybka, ale nie działa z DST)
  • Moja metoda 3: 0,1255 ms
  • Moja metoda 2: 0.1289 ms
  • Ben Lee DATE_FORMAT metoda: 0,1495 ms
  • Moja metoda 1: 0,1506 ms

12
2017-10-02 04:26



Zaznacz mnie, ponieważ chciałem po prostu uciąć - MikeKulls
DATE_FORMAT jest wolny? Nigdy o tym nie słyszałem. Czy masz referencje / testy porównawcze? Nie mogę znaleźć niczego na temat Google DATE_FORMATo słabej wydajności i nic nie wskazuje, że wzywa MINUTE() i SECOND() byłaby znacznie szybsza niż połączenie DATE_FORMAT. W każdym razie, czy żadna różnica w wydajności nie powinna być na poziomie nanosekundy - zasadniczo niewidoczna / nieistotna w prawie każdym rzeczywistym celu? - Ben Lee
@ BenLee Spodziewałem się, że manipulowanie ciągami i analizowanie dat będzie znacznie wolniejsze niż MINUTE/SECOND, ale po profilowaniu dwóch przypadków, które nie są prawdziwe. Twoje rozwiązanie jest nawet potencjalnie nieco szybsze niż moje (być może z powodu mojego połączenia telefonicznego MINUTE i SECOND dwa razy?). Jednak mój przykład, który pomija sekundy, jest szybszy niż DATE_FORMAT. Zaktualizuję moją odpowiedź. - Code Commander
Aby uzyskać informacje od innych osób, skróć do innych interwałów minutowych (np. 15 minut): wybierz timestamp,date_sub(timestamp,interval (minute(timestamp) % 15)* 60 +second(timestamp) second)... - Steve Bennett


Od Jak zaokrąglić DateTime w MySQL?:

Jest to trochę nieprzyjemne, gdy robisz to z danymi datetime; miły kandydat do funkcji przechowywanej.

DATE_SUB(DATE_SUB(time, INTERVAL MOD(MINUTE(time),5) MINUTE ), 
         INTERVAL SECOND(time) SECOND)

Jest to łatwiejsze, gdy używasz znaczników czasu UNIXTIME, ale jest to ograniczone do zakresu dat od 1970 do 2038.

FROM_UNIXTIME(UNIX_TIMESTAMP(time) - MOD(UNIX_TIMESTAMP(time),300))

Powodzenia.


5
2018-03-13 07:53



Ostrożnie z tym. Czas unixowy nie działa dla dat, które mieszczą się między zmianami czasu letniego. Na przykład: select FROM_UNIXTIME(UNIX_TIMESTAMP('2012-03-11 2:14:00') - MOD(UNIX_TIMESTAMP('2012-03-11 2:14:00'),300)); - Code Commander


To oznacza powrót do następnej godziny '2012-01-02 18:02:30' zostaną przekształcone w '2012-01-02 19:00:00'

TIMESTAMPADD(HOUR,
    TIMESTAMPDIFF(HOUR,CURDATE(),timestamp_column_name),
    CURDATE())

Zamiast CURDATE() możesz na przykład użyć dowolnej daty '2000-01-01' Nie wiem, czy mogą wystąpić problemy z korzystaniem CURDATE() jeśli data systemu zmienia się między dwoma wywołaniami funkcji, nie wiem, czy Mysql wywoła oba w tym samym czasie.

aby uzyskać najbliższy godzina będzie:

TIMESTAMPADD(MINUTE,
    ROUND(TIMESTAMPDIFF(MINUTE,CURDATE(),timestamp_column_name)/60)*60,
    CURDATE())

zmiana o 60 na 15 dostanie najbliższy 15-minutowy interwał, za pomocą SECOND można uzyskać najbliższy żądany drugi interwał itd.

Aby uzyskać dostęp do poprzedniej godziny TRUNCATE() lub FLOOR() zamiast ROUND().

Mam nadzieję że to pomoże.


1
2018-03-25 12:48





Jeśli chcesz zaokrąglić czas do następnej godziny, możesz użyć tego:

SELECT TIME_FORMAT(
  ADDTIME(
    TIMEDIFF('16:15', '10:00'), '00:59:00'
  ),
  '%H:00:00'
)

0
2017-11-30 09:17





Myślę, że jest to najlepszy sposób, ponieważ wykorzysta również najmniej zasobów

date_add(date(date_completed), interval hour(date_completed) hour) as date_hr

0
2018-03-12 19:12