SQL-передача таблицы даты за дату

Интересно, как я могу передать RECEIVEDDATETIME оператору ниже. Что мне не хватает в моем операторе SQL?

Благодаря Марку Баринштейну я добавил внутреннее соединение к таблицам CALENDAR и TESTDATA, чтобы передать T.RECEIVEDDATETIME в качестве даты из исходного примера.

Этот оператор получает C.WORKDATE из моего tblCalendar, но мне нужно передать T.RECEIVEDDATETIME, чтобы получить желаемую "DUEDATE".

Я создал «tblCalendar», потому что читал, что проще ссылаться на календарь для настоящих рабочих дней... чтобы исключить выходные и праздничные дни и учесть високосные годы. Не уверен, что это лучшая практика, но, похоже, прямо не кодирует исключения. Поэтому я создал tblCalendar, который включает ВСЕ ДАТЫ с 2017 по 2050 год и праздники. Приведенные ниже данные лишь частично отражают январь 2019 года, так как я не нашел способа прикрепить сюда таблицу:

tblCalendar (partial)
DATE        NUMDAYOFWK       DAYOFWK      HOLIDAY
01/01/2019    3              Tuesday      YES
01/02/2019    4              Wednesday  
01/03/2019    5              Thursday   
01/04/2019    6              Friday 
01/05/2019    7              Saturday   
01/06/2019    1              Sunday 
01/07/2019    2              Monday 
01/08/2019    3              Tuesday    
01/09/2019    4              Wednesday  
01/10/2019    5              Thursday   
01/11/2019    6              Friday 
01/12/2019    7              Saturday   
01/13/2019    1              Sunday 
01/14/2019    2              Monday 
01/15/2019    3              Tuesday    
01/16/2019    4              Wednesday  
01/17/2019    5              Thursday   
01/18/2019    6                  Friday 
01/19/2019    7              Saturday   
01/20/2019    1              Sunday 
01/21/2019    2              Monday       YES

Таблица tblTestData содержит основные данные, где я ссылаюсь на все поля, необходимые для моих отчетов.

tblTestData Columns (partial) - DeliveryDays would reference the 2nd parameter BusDayAdd that was noted in the previous SQL.

ID                  RECEIVEDDATE       DeliveryDays     Address
T-20190116-255      01/16/2019          2             1234 Address
T-20190117-255      01/17/2019          2             3657 Address
T-20190118-222      01/18/2019          2             9999 Address
T-20190119-255      01/19/2019          2
T-20190120-255      01/20/2019
T-20190121-255      01/21/2019
T-20190303-1        03/03/2019

Желаемые конечные результаты будут выглядеть следующим образом, принимая во внимание RECEIVEDDATETIME в моем tblTestData и ссылаясь на таблицу tblCalendar, чтобы исключить выходные и праздничные дни, чтобы указать правильную дату выполнения.

ID              RECEIVEDDATE            DeliveryDays    DueDate    Address
T-20190116-255  1/16/2019                2             1/18/2019     1234 Address
T-20190117-255  1/17/2019   2   1/22/2019   3657 Address
T-20190118-222  1/18/2019   2   1/23/2019   9999 Address
T-20190119-255  1/19/2019   2   1/23/2019   10000 Address
T-20190120-255  1/20/2019   2   1/23/2019   10001 Address
T-20190121-255  1/21/2019   2   1/23/2019   10002 Address
T-20190121-256  1/22/2019   2   1/24/2019   10003 Address
T-20190303-1    3/3/2019    3   3/6/2019    10004 Address
T-20190121-257  3/15/2019   7   3/26/2019   10005 Address

Я пробовал различные операторы, переписывая код, чтобы обернуть строку SQL для передачи таблицы «RECEIVEDDATETIME», но каждый раз, когда «DUEDATE» возвращается {NULL}.

SELECT T.ID, VARCHAR_format(T.RECEIVEDDATETIME, 'MM/DD/YYYY') RECDATE, 

(select VARCHAR_FORMAT(WORKDATE,'MM/DD/YYYY') DUEDATE 

from 

(Select
WORKDATE, T.RECEIVEDDATETIME,
sum(case when C.HOLIDAY='YES' or C.NUMDAYOFWK in (7,1) then 0 else 1 end) over  (order by C.WORKDATE) BUSDAYADD

from tblCALENDAR C

--ADDED INNER JOIN TO GET T.RECEIVEDDATETIME TO FEED AUTOMATICALLY FROM TESTDATA TABLE

INNER JOIN TESTDATA T
      ON 
VARCHAR_FORMAT(C.WORKDATE, 'MM/DD/YYYY') = VARCHAR_FORMAT(T.RECEIVEDDATETIME,'MM/DD/YYYY')

where C.WORKDATE > VARCHAR_FORMAT(T.RECEIVEDDATETIME,'MM/DD/YYYY')) -- 1-st PARAMETER TO CAPTURE RECEIVEDDATETIME 

WHERE BUSDAYADD = ? -- 2-nd parameter to add the number of days needed to be added to RECEIVEDDATETIME 

order by WORKDATE --3rd Parameter
fetch first 1 row only) 

FROM TESTDATA T
WHERE ID = 'T-20190303-1'

Когда я запускаю SQL, я получаю {NULL} для своих результатов для DUEDATE:

ID              RECDATE     DUEDATE
T-20190303-1    03/03/2019  {NULL}

Результаты должны быть:

 ID             RECDATE     DUEDATE
 T-20190303-1   03/03/2019  03/05/2019

Любая помощь приветствуется.

Вы должны предоставить свои тестовые данные в обеих таблицах (также с типами столбцов) и требуемый результат. Пожалуйста, перепишите свой вопрос с этой дополнительной информацией.

Mark Barinstein 26.05.2019 09:44
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
0
1
49
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

SELECT для DUEDATE

INNER JOIN TESTDATA T
   ON VARCHAR_FORMAT(C.WORKDATE, 'MM/DD/YYYY') = VARCHAR_FORMAT(T.RECEIVEDDATETIME,'MM/DD/YYYY')
where C.WORKDATE > VARCHAR_FORMAT(T.RECEIVEDDATETIME,'MM/DD/YYYY'))

Это означает, что вы присоединяетесь к Equality, а затем ограничиваетесь Workdate > Receiveddatetime. может в этом проблема...

Ответ принят как подходящий

Вы указали несогласованные данные в обеих таблицах: ваш календарь заканчивается слишком рано для всех записей в таблице tblTestData, кроме 1-й.
Позвольте мне предоставить абсолютно такой же запрос, который я уже отправил ранее на ваш другой вопрос.

with tblCalendar (DATE, HOLIDAY) as (values
  (date(to_date('01/16/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/17/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/18/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/19/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/20/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/21/2019', 'MM/DD/YYYY')), 'YES')

, (date(to_date('01/22/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/23/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/24/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/25/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/26/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/27/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/28/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/29/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/30/2019', 'MM/DD/YYYY')), '')
, (date(to_date('01/31/2019', 'MM/DD/YYYY')), '')
, (date(to_date('02/01/2019', 'MM/DD/YYYY')), '')
, (date(to_date('02/02/2019', 'MM/DD/YYYY')), '')
, (date(to_date('02/03/2019', 'MM/DD/YYYY')), '')
, (date(to_date('02/04/2019', 'MM/DD/YYYY')), '')
, (date(to_date('02/05/2019', 'MM/DD/YYYY')), '')

)
, tblTestData (ID, RECEIVEDDATE, DeliveryDays) as (values
  ('T-20190116-255', date(to_date('01/16/2019', 'MM/DD/YYYY')), 2)
, ('T-20190117-255', date(to_date('01/17/2019', 'MM/DD/YYYY')), 2)
, ('T-20190118-222', date(to_date('01/18/2019', 'MM/DD/YYYY')), 2)
, ('T-20190119-255', date(to_date('01/19/2019', 'MM/DD/YYYY')), 2)
, ('T-20190120-255', date(to_date('01/20/2019', 'MM/DD/YYYY')), 2)
, ('T-20190121-255', date(to_date('01/21/2019', 'MM/DD/YYYY')), 2)
, ('T-20190121-256', date(to_date('01/22/2019', 'MM/DD/YYYY')), 2)
, ('T-20190303-1'  , date(to_date('01/23/2019', 'MM/DD/YYYY')), 3)
, ('T-20190121-257', date(to_date('01/24/2019', 'MM/DD/YYYY')), 7)
)
select m.*, t.date as DUEDATE
--, dayofweek(date) as DAYOFWK, dayname(date) as DAY
from tblTestData m
, table
(
  select date
  from table 
  (
    select 
      date
    , sum(case when HOLIDAY='YES' or dayofweek(date) in (7,1) then 0 else 1 end) over (order by date) as dn_
    from tblCalendar t
    where t.date > m.RECEIVEDDATE
  )
  where dn_ = m.DeliveryDays
  fetch first 1 row only
) t;

Результат:

ID              RECEIVEDDATE DAYS   DUEDATE
--------------  ------------ ----   ----------
T-20190116-255    2019-01-16    2   2019-01-18
T-20190117-255    2019-01-17    2   2019-01-22
T-20190118-222    2019-01-18    2   2019-01-23
T-20190119-255    2019-01-19    2   2019-01-23
T-20190120-255    2019-01-20    2   2019-01-23
T-20190121-255    2019-01-21    2   2019-01-23
T-20190121-256    2019-01-22    2   2019-01-24
T-20190303-1      2019-01-23    3   2019-01-28
T-20190121-257    2019-01-24    7   2019-02-04

Спасибо; теперь это работает, увидев ваш пример с моими тестовыми данными. Приносим свои извинения за несоответствие данных.

SQLUSER 29.05.2019 19:09

Другие вопросы по теме