Усечение временных меток - PullRequest
       33

Усечение временных меток

5 голосов
/ 24 февраля 2011

Предположим, у меня есть переменная отметки времени:

select timestamp '2011-02-24 08:30:42 +06:00' from dual;

Есть ли способ "усечь" что-то вроде

'2011-02-24 08:00:00 +06:00'

(я сократил минуты и секунды, но покинул часовой пояс)

Целевая версия Oracle - 11g r2

Ответы [ 4 ]

4 голосов
/ 24 февраля 2011
SQL> select to_timestamp_tz(to_char(timestamp '2011-02-24 08:30:42 +06:00', 'YYYY-MM-DD HH24 TZH:TZM'), 'YYYY-MM-DD HH24 TZH:TZM') from dual;

TO_TIMESTAMP_TZ(TO_CHAR(TIMESTAMP'2011-02-2408:30:42+06:00','YYYY-MM-DDTZH:
---------------------------------------------------------------------------
24.02.2011 8:00:00,000000000 +06:00
1 голос
/ 04 декабря 2013

Ваш NLS_DATE_FORMAT, вероятно, настроен на отображение только части даты.Это работает для меня:

SELECT 
    to_char( TRUNC(timestamp'2011-02-24 08:30:42 +06:00', 'HH'), 'YYYY-MM-DD HH24:MI:SS' )  
FROM DUAL;

Имейте в виду, что возвращаемый результат - ДАТА, поэтому вы теряете любую информацию о локализации.Вы можете вернуть нормализованную по времени GMT метку времени, приведя результат к метке времени:

SELECT 
    to_char( from_tz( cast( TRUNC(timestamp'2011-02-24 08:30:42 +06:00' at time zone 'GMT', 'HH' ) as timestamp ), 'GMT' ), 'YYYY-MM-DD HH24:MI:SS TZR' )
FROM DUAL;

Чтобы сохранить информацию о часовом поясе, вы должны сделать что-то довольно запутанное.Может быть проще использовать хранимую функцию для выполнения преобразования в этой точке.Это работает так же, как встроенная в Oracle функция TRUNC ():

create or replace function trunc_timestamp(
    ts  in timestamp_tz_unconstrained,
    fmt in varchar2 
)
return timestamp_tz_unconstrained
is
    tzone  varchar2(20);
begin
    tzone := extract( timezone_region from ts );
    if tzone = 'UNKNOWN' then
        tzone := to_char( extract( timezone_hour from ts ), 'fm09' ) 
          || ':' 
          || to_char( extract( timezone_minute from ts ), 'fm09' );
    end if;
    return from_tz( cast( TRUNC( ts at time zone tzone, fmt ) as timestamp ), tzone );
end;
/

Я создал sqlfiddle для демонстрации.

1 голос
/ 24 февраля 2011

Я заставил его работать, используя:

SELECT TO_TIMESTAMP_TZ(TO_CHAR(timestamp '2011-02-24 08:30:42 +06:00', 'YYYY-MM-DD HH24') || ':00:00 '|| TO_CHAR(timestamp '2011-02-24 08:30:42 +06:00', 'TZH:TZM'), 'YYYY-MM-DD HH24:MI:SS TZH:TZM')
  FROM DUAL

TRUNC поддерживает отметки времени 9.2.0.3 + , но в моем тестировании на 10g Express Edition это

SELECT TRUNC(timestamp '2011-02-24 08:30:42 +06:00', 'HH')
  FROM DUAL

... полностью облажались часы и AM / PM.Не имеет значения для литерала или для него, если он указан внутри TO_TIMESTAMP_TZ.Документация для TRUNC (date) для 10gR2 гласит: «Возвращаемое значение всегда имеет тип данных DATE, даже если для даты указан другой тип данных datetime».

0 голосов
/ 29 сентября 2011

Попробуйте select cast(timestamp as date) from dual

...