Member 14636607 Ответов: 2

Разбить одну строку на несколько строк на основе значения столбца


I have following quantity table 

<pre>Item	QuantityRequired	MaxQuantity
 Item1	      200	               50
 Item2	      100	               30


Основываясь на значении столбца MaxQuantity, строки таблицы должны быть разделены, как показано ниже,

Item	QuantityRequired
Item1	  50
Item1	  50
Item1	  50
Item1	  50
Item2	  30
Item2	  30
Item2	  30
Item2	  10


Что я уже пробовал:

Я треид с Союзом своим не работаю.

CHill60

Покажите код, который вы пробовали

2 Ответов

Рейтинг:
5

Richard Deeming

Вот решение с помощью одного рекурсивный CTE[^]:

WITH cte As
(
    SELECT
        Item,
        CASE
            WHEN QuantityRequired > MaxQuantity THEN MaxQuantity
            ELSE QuantityRequired
        END As QuantityRequired,
        QuantityRequired - MaxQuantity As RemainingQuantity,
        MaxQuantity
    FROM
        YourTable
    
    UNION ALL
    
    SELECT
        Item,
        CASE
            WHEN RemainingQuantity > MaxQuantity THEN MaxQuantity
            ELSE RemainingQuantity
        END As QuantityRequired,
        RemainingQuantity - MaxQuantity As RemainingQuantity,
        MaxQuantity
    FROM
        cte
    WHERE
        RemainingQuantity > 0
)
SELECT
    Item,
    QuantityRequired
FROM
    cte
ORDER BY
    Item
;
Выход:
Item    QuantityRequired
------------------------
Item1	50
Item1	50
Item1	50
Item1	50

Item2	30
Item2	30
Item2	30
Item2	10


Member 14636607

БЛАГОДАРЮ ВАС СЭР

Рейтинг:
19

CHill60

Для этого я решил использовать рекурсивный CTE (Common Table Expression) в сочетании с другим CTE

;with cte1 as
(
	select item, quantityrequired, maxquantity, 
	cast(QuantityRequired / maxquantity as integer) as wholes, QuantityRequired % MaxQuantity as partials
	from #test
)
,cte2 as 
(
    SELECT item, maxquantity, wholes, 'base ' as w from cte1
    UNION ALL
    SELECT item, maxquantity, wholes - 1, 'recur' as w
    FROM cte2 WHERE wholes > 1
)
SELECT item, MaxQuantity as QuantityRequired 
from cte2
union all
SELECT item, partials as QuantityRequired 
from cte1 where partials > 0
order by Item, QuantityRequired desc


Edit - хотел объяснить это до того, как я его отправил!

Первый CTE определяет, сколько строк мне нужно, wholes это количество строк, в которых я могу использовать максимально допустимое количество (обязательно / макс.), partialsэто то, что осталось (требуется mod max)

2-й CTE генерирует все необходимые "целые" строки - я включил этот столбец w, чтобы помочь вам увидеть, что происходит (если вы хотите включить его в select) - полное объяснение рекурсивных CTE можно найти по адресу Рекурсивных обобщенных табличных выражениях объяснил - необходимые для SQL[^]

Окончательный выбор принимает все эти "целые" строки и объединения с оставшимся "частичным" значением для каждого элемента- если таковой имеется. Обратите внимание на использование Союза все таким образом, дубликаты "целых" строк не удаляются


Member 14636607

БЛАГОДАРЮ ВАС СЭР