Oracle
 sql >> Base de Dados >  >> RDS >> Oracle

Como você seleciona um campo varchar2 no formato de 'HH24:MI:SSxFF6' como um INTERVAL HOUR TO SECOND(6)?


Você pode usar o TO_DSINTERVAL função ; exemplo aqui usando um CTE para replicar sua tabela:
WITH some_table AS (SELECT '00:00:00.000000' AS time_field FROM dual)
SELECT TO_DSINTERVAL('0 ' || time_field)
FROM some_table;

TO_DSINTERVAL('0'||TIME_FIELD)
---------------------------------------------------------------------------
+000000000 00:00:00.000000000

Observe que para tornar o formato algo que a função reconheça, você deve fornecer uma parte de 'dias', portanto, o prefixo do dummy '0 ' corda.

Sua consulta de valor fixo retorna um formato ligeiramente diferente (ou pelo menos exibe um pouco diferente; tipos daa de intervalo não têm modelos de formato da mesma forma que as datas, então não tenho certeza de como expressar isso com precisão):
SELECT INTERVAL '00:00:00.000000' HOUR TO SECOND(6)
FROM DUAL;

INTERVAL'00:00:00.000000'HOURTOSECOND(6)
---------------------------------------------------------------------------
+00 00:00:00.000000

Para replicar isso, você pode cast isso se você precisar:
WITH some_table AS (SELECT '00:00:00.000000' AS time_field FROM dual)
SELECT CAST(TO_DSINTERVAL('0 ' || time_field) AS INTERVAL DAY TO SECOND(6))
FROM some_table;

CAST(TO_DSINTERVAL('0'||TIME_FIELD)ASINTERVALDAYTOSECOND(6))
---------------------------------------------------------------------------
+00 00:00:00.000000

... ou apenas:
WITH some_table AS (SELECT '00:00:00.000000' AS time_field FROM dual)
SELECT CAST('0 ' || time_field AS INTERVAL DAY TO SECOND(6))
FROM some_table;

CAST('0'||TIME_FIELDASINTERVALDAYTOSECOND(6))
---------------------------------------------------------------------------
+00 00:00:00.000000

... que é praticamente o que @catcall sugeriu primeiro, mas isso também precisa do '0 ' prefixado ou você recebe um ORA-01867 . (Ou, se você tentar usar HOUR TO SECOND , ORA-00963 , mesmo com o valor do dia prefixado). No entanto, eu acho (e é apenas um palpite, embora muito pouco educado) que está fazendo um TO_DSINTERVAL implícito ou similar, e acho que prefiro usar um explícito para ter certeza do que está acontecendo. Mas pode ser só eu...

Usando seus dados de amostra, também recebo um ORA-01867 , mas é causado pelo valor nulo. Você pode usar um case para deixar isso como nulo no resultado:
SELECT CASE WHEN time_field IS NULL THEN null
    ELSE CAST('0 ' || time_field AS INTERVAL DAY TO SECOND(6)) END
FROM some_table;

CASEWHENTIME_FIELDISNULLTHENNULLELSECAST('0'||TIME_FIELDASINTERVALDAYTOSECO
---------------------------------------------------------------------------
+00 10:00:00.000000
+00 12:00:00.000000
+00 15:00:00.000000
+00 17:00:00.000000
+00 20:00:00.000000


6 rows selected.