SQL Self-Join Обнаружить иерархию - PullRequest
0 голосов
/ 29 сентября 2019

Рассмотрим таблицу SQL Server 2017 (назовем ее «Продукты»), которая имеет подразумеваемую иерархию, основанную на упорядочении первичного ключа (id) со следующей логической структурой:

Product (root)
 - SKU  (optional children)
 - Rule (optional children)

Пример таблицы может выглядеть следующим образомthis:

    ID  Item_Type
    1   Product
    2     SKU
    3     SKU
    4     SKU
    5     Rule
    6     Rule
    7   Product
    8     Rule
    9     Rule
    10  Product
    11    SKU

Учитывая, что я хочу найти родительский продукт каждого SKU и правила, каким будет соответствующий запрос?Результаты должны быть такими:

ID  Item_Type ProductId
2     SKU     1
3     SKU     1
4     SKU     1
5     Rule    1
6     Rule    1
8     Rule    7
9     Rule    7
11    SKU     10

Ответы [ 2 ]

0 голосов
/ 29 сентября 2019

Скалярная функция тоже может пригодиться

CREATE FUNCTION FindParentKey
(
    @CurrentItemKey int
)
RETURNS int
AS
BEGIN
    return (
        SELECT MAX(ID)
        FROM Product
        WHERE ID < @CurrentItemKey and Item_Type = 'Product'
    )
END
GO

SELECT ID, Item_Type, dbo.FindParentKey(ID)
FROM Product
WHERE Item_Type <> 'Product'
0 голосов
/ 29 сентября 2019

Я думаю, что нашел решение.Вероятно, не самый лучший подход, но, похоже, он достаточно эффективен:

select childid, item_type, max(parentId) as productid from (
    select children.*, parents.id as parentId from (
        select id as childId, Item_Type from products where Item_Type in ('SKU', 'RULE')
    ) children
    inner join (
        select id from products 
        where Item_Type in ('Product')
    ) parents
    on parents.id < children.childId
) hierearchy
group by childid, item_type
order by childid
...