Сумма по дням и пунктам и добавление недостающих дней - PullRequest
0 голосов
/ 27 марта 2020

У меня есть таблица с изменениями запасов для определенных предметов. Я хотел бы суммировать по StockPostingQuantity и за каждый день и каждый ItemID. Тем не менее, я также хотел бы заполнить пропущенные дни для каждого ItemID, поэтому у меня будет ежедневный запас, даже если для определенного дня нет записей. Я хотел бы заполнить все дни для 2017, 2018 и 2019 годов.

Пример ниже.

Как это можно сделать на сервере T-SQL / SQL? Я работаю на SQL Server 2016.

+-------------------------+--------+---------------------------+
|      CalendarDate       | ItemID |   StockPostingQuantity    |
+-------------------------+--------+---------------------------+
| 2019-09-13 00:00:00.000 |  42937 |   24.00000000000000000000 |
| 2019-09-17 00:00:00.000 |  42937 |   14.00000000000000000000 |
| 2019-09-18 00:00:00.000 |  42937 |  232.00000000000000000000 |
| 2019-09-20 00:00:00.000 |  42937 |  933.00000000000000000000 |
| 2019-09-11 00:00:00.000 |  44337 |  144.00000000000000000000 |
| 2019-09-12 00:00:00.000 |  44337 |  288.00000000000000000000 |
| 2019-09-13 00:00:00.000 |  44337 |  720.00000000000000000000 |
| 2019-09-16 00:00:00.000 |  44337 | 3384.00000000000000000000 |
| 2019-09-17 00:00:00.000 |  44337 | 1771.00000000000000000000 |
+-------------------------+--------+---------------------------+

+-------------------------+--------+---------------------------+--------------------------+
|      CalendarDate       | ItemID |   StockPostingQuantity    |          Total           |
+-------------------------+--------+---------------------------+--------------------------+
| 2019-09-13 00:00:00.000 |  42937 |   24.00000000000000000000 |  24.00000000000000000000 |
| 2019-09-14 00:00:00.000 |  42937 |   24.00000000000000000000 |  24.00000000000000000000 |
| 2019-09-15 00:00:00.000 |  42937 |   24.00000000000000000000 |  24.00000000000000000000 |
| 2019-09-16 00:00:00.000 |  42937 |   24.00000000000000000000 |  24.00000000000000000000 |
| 2019-09-17 00:00:00.000 |  42937 |   14.00000000000000000000 |  36.00000000000000000000 |
| 2019-09-18 00:00:00.000 |  42937 |  232.00000000000000000000 |  268.0000000000000000000 |
| 2019-09-19 00:00:00.000 |  42937 |   24.00000000000000000000 |  292.0000000000000000000 |
| 2019-09-20 00:00:00.000 |  42937 | -933.00000000000000000000 | -641.0000000000000000000 |
| 2019-09-11 00:00:00.000 |  44337 |  144.00000000000000000000 | 144.00000000000000000000 |
| 2019-09-12 00:00:00.000 |  44337 |  288.00000000000000000000 | 432.00000000000000000000 |
| 2019-09-13 00:00:00.000 |  44337 |  720.00000000000000000000 | 1152.0000000000000000000 |
| 2019-09-14 00:00:00.000 |  44337 |  720.00000000000000000000 | 1152.0000000000000000000 |
| 2019-09-15 00:00:00.000 |  44337 |  720.00000000000000000000 | 1152.0000000000000000000 |
| 2019-09-16 00:00:00.000 |  44337 | 3384.00000000000000000000 | 4536.0000000000000000000 |
| 2019-09-17 00:00:00.000 |  44337 | -1771.0000000000000000000 | 2765.0000000000000000000 |
+-------------------------+--------+---------------------------+--------------------------+

1 Ответ

1 голос
/ 27 марта 2020

Вы можете следовать логике c ниже:

DECLARE @DataSource TABLE
(
    [CalendarDate] DATETIME2(0)
   ,[ItemID] INT
   ,[StockPostingQuantity] DECIMAL(9,2)
);

INSERT INTO @DataSource ([CalendarDate], [ItemID], [StockPostingQuantity])
VALUES ('2019-09-13 00:00:00.000', 42937,  24.00000000000000000000)
      ,('2019-09-17 00:00:00.000', 42937,  14.00000000000000000000)
      ,('2019-09-18 00:00:00.000', 42937, 232.00000000000000000000)
      ,('2019-09-20 00:00:00.000', 42937, -933.00000000000000000000)
      ,('2019-09-11 00:00:00.000', 44337, 144.00000000000000000000)
      ,('2019-09-12 00:00:00.000', 44337, 288.00000000000000000000)
      ,('2019-09-13 00:00:00.000', 44337, 720.00000000000000000000)
      ,('2019-09-16 00:00:00.000', 44337, 3384.00000000000000000000)
      ,('2019-09-17 00:00:00.000', 44337, -1771.00000000000000000000);

WITH DataSource AS
(
    SELECT ROW_NUMBER() OVER (PARTITION BY [ItemID] ORDER BY [CalendarDate] ASC) AS [RowID]
          ,SUM([StockPostingQuantity]) OVER (PARTITION BY [ItemID] ORDER BY [CalendarDate] ASC) AS [Total]
          ,*
    FROM @DataSource
)
SELECT IIF([NewDate] = 1 OR DS2.[RowID] IS NULL, DS1.[CalendarDate], DATEADD(DAY, [NewDate] - 1, DS1.[CalendarDate])) AS [CalendarDate]
      ,DS1.[ItemID]
      ,DS1.[StockPostingQuantity]
      ,DS1.[Total]
FROM DataSource DS1
LEFT JOIN DataSource DS2
    ON DS1.[ItemID] = DS2.[ItemID]
    AND DS1.[RowID] = DS2.[RowID] - 1
OUTER APPLY
(
    SELECT DISTINCT n = number 
    FROM master..[spt_values] 
    WHERE number BETWEEN 1 AND DATEDIFF(DAY, DS1.[CalendarDate], DS2.[CalendarDate])    
) Dates([NewDate]);

enter image description here

Логи c:

  1. упорядочить записи и вычислить общее число
  2. присоединить дату к следующей и вычислить разницу дат
  3. создать пропущенные строки и пропущенные даты
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...