#sql #oracle
#sql #Oracle
Вопрос:
У меня в таблице 4 столбца RUNNING_INFO
TRAIN_START_DATE VARCHAR2(8)
SCHEDULED_DATE VARCHAR2(8)
ACTUAL_DATE VARCHAR2(8)
SCHEDULED_TIME VARCHAR2(8)
ACTUAL_TIME VARCHAR2(8)
Я должен извлечь минуты из фактической / запланированной даты и времени, для этого я написал следующий код
SELECT TRAIN_START_DATE,SCHEDULED_DATE,ACTUAL_DATE,SCHEDULED_TIME,ACTUAL_TIME,
CEIL((TO_DATE(concat(ACTUAL_DATE, ACTUAL_TIME) , 'DD-Mon-YYYYHH24:MI:SS') - TO_DATE(TRAIN_START_DATE, 'DD-Mon-YYYY'))*1440) as ACTUAL_MINS ,
CEIL((TO_DATE(concat(SCHEDULED_DATE, SCHEDULED_TIME) , 'DD-Mon-YYYYHH24:MI:SS') - TO_DATE(TRAIN_START_DATE, 'DD-Mon-YYYY'))*1440) as SCH_MINS FROM RUNNING_INFO
Но я не получаю правильные значения в ACTUAL_MINS и SCH_MINS , например, для следующего набора строк выходных данных значения поступают неправильно в минутах :
Пожалуйста, объясните, как правильно находить минуты.
Комментарии:
1. Какие значения вы хотите?
2. для первой строки фактические минуты составляют 1449, это должно быть 1440 8 = 1448 правильно, аналогично можно проверить для других строк
3. Ваш дизайн данных фатально испорчен. Вы никогда не должны хранить дату как что-либо, кроме ДАТЫ. И тип данных ДАТЫ включает время, вплоть до секунды, поэтому нет никакой необходимости в ваших столбцах SCHEDULED_TIME и ACTUAL_TIME. Я бы написал пример решения в качестве ответа, но я не понимаю, что на самом деле представляет собой «фактические минуты». Но я абсолютно уверен в двух вещах. Во-первых, если вы исправите свою модель данных, ваше решение станет тривиальным. Во-вторых, если вы не исправите свою модель данных, это только вопрос времени, когда вы вернетесь сюда с ошибками формата.
4. Модель данных не может быть изменена
5. @radha . . . Вычтите 1.
Ответ №1:
минуты между двумя датами, в которые эти даты включают время, составляют
( date1 - date2 ) * 1440
в вашем случае, когда дата / время разделены на два столбца, вы можете объединить их в дату, поэтому что-то вроде
to_date(to_char(sched_date,'yyyymmdd')||sched_time,'yyyymmddhh24:mi:ss')
для каждой даты перед выполнением вычитания. И тогда вам не нужен CEIL, потому что с плавающей запятой округляется даже самая маленькая десятичная дробь
SQL> with t as
2 (
3 select
4 '04-sep-2020' x1,
5 '22:02:00' x2,
6 '05-sep-2020' x3,
7 '00:08:00' x4
8 from dual
9 )
10 SELECT
11 CEIL((TO_DATE(concat(x1, x2) , 'DD-Mon-YYYYHH24:MI:SS') - TO_DATE(x3, 'DD-Mon-YYYY'))*1440) as ACTUAL_MINS ,
12 CEIL((TO_DATE(concat(x3, x4) , 'DD-Mon-YYYYHH24:MI:SS') - TO_DATE(x1, 'DD-Mon-YYYY'))*1440) as SCH_MINS
13 FROM t;
ACTUAL_MINS SCH_MINS
----------- ----------
-118 1449
SQL>
SQL> with t as
2 (
3 select
4 '04-sep-2020' x1,
5 '22:02:00' x2,
6 '05-sep-2020' x3,
7 '00:08:00' x4
8 from dual
9 )
10 SELECT
11 (TO_DATE(concat(x1, x2) , 'DD-Mon-YYYYHH24:MI:SS') - TO_DATE(x3, 'DD-Mon-YYYY'))*1440 as ACTUAL_MINS ,
12 (TO_DATE(concat(x3, x4) , 'DD-Mon-YYYYHH24:MI:SS') - TO_DATE(x1, 'DD-Mon-YYYY'))*1440 as SCH_MINS
13 FROM t;
ACTUAL_MINS SCH_MINS
----------- ----------
-118 1448
SQL>
Комментарии:
1. Приношу свои извинения, я неправильно истолковал ваш первоначальный вопрос. Я обновил ответ