2016-07-12 4 views
0

Имея эту таблицу:Как удалить все узлы данного корня в списке смежности SQL

enter image description here

Я хочу, чтобы удалить корневой узел, путем отправки запроса ID = 1 и я хочу, чтобы все подносы этого идентификатора также будут удалены.

как я могу это сделать?

+2

Итак, если вы удалите 'ID = 1' нужно удалить три записи? Не могли бы вы показать больше записей из таблицы? – gotqn

+0

@gotqn Да, это правда. нет больше, это пример таблицы. у вас может быть больше записей, таких как Id 4 Name 2 Owner 2 Parent NULL и т. д. – eyalewin

ответ

2

Это может быть сделано с помощью рекурсивного общего табличного выражения.

Чтобы получить все дети одного узла вы можете использовать:

with tree as (
    select id, parent 
    from eyalewin 
    where id = 1 
    union all 
    select c.id, c.parent 
    from eyalewin c 
    join tree p on p.id = c.parent 
) 
select * 
from tree; 

Это может быть использовано для удаления всех из них:

with tree as (
    select id, parent 
    from eyalewin 
    where id = 1 
    union all 
    select c.id, c.parent 
    from eyalewin c 
    join tree p on p.id = c.parent 
) 
delete from eyalewin 
where id in (select id 
      from tree); 
2

Допустим, у вас есть следующие данные:

enter image description here

и вы хотите удалить запись 2.1 и всех его потомков (в данном случае 2.1.3 только). Вы можете использовать следующий код, чтобы получить IDs, который должен быть удален:

WITH DataSource ([ID], [HierarchyLevel]) AS 
(
    SELECT [ID] 
      ,CAST(REPLACE('/' + [Name] + '/', '.', '/') AS HIERARCHYID) 
    FROM @DataSource 
) 
SELECT [ID] 
     ,[HierarchyLevel].ToString() 
FROM DataSource 
WHERE [HierarchyLevel].IsDescendantOf('/2/1/') = 1; 

enter image description here

В основном, мы превратим вашу запись в hierarchy id типа и использовать встроенные IsDescendantOf функции, чтобы получить все childs из узел.

Это полный рабочий пример:

DECLARE @DataSource TABLE 
(
    [ID] TINYINT 
    ,[Name] VARCHAR(12) 
    ,[Owner] VARCHAR(12) 
    ,[Parent] INT 
); 

INSERT INTO @DataSource ([ID], [Name], [Owner], [Parent]) 
VALUES (1, '1', '1', NULL) 
     ,(2, '1.1', '1.1', 1) 
     ,(3, '1.1.1', '1.1.1', 2) 
     ,(4, '2', '2.1', NULL) 
     ,(5, '2.1', '2.1', 4) 
     ,(6, '2.2', '2.2', 4) 
     ,(7, '2.1.3', '2.1.3', 5); 


WITH DataSource ([ID], [HierarchyLevel]) AS 
(
    SELECT [ID] 
      ,CAST(REPLACE('/' + [Name] + '/', '.', '/') AS HIERARCHYID) 
    FROM @DataSource 
) 
DELETE @DataSource 
FROM @DataSource DS 
INNER JOIN DataSource DS1 
    ON DS.[ID] = DS1.[ID] 
WHERE [HierarchyLevel].IsDescendantOf('/2/1/') = 1; 

SELECT * 
FROM @DataSource;