Продолжаем тему деревов. :)
Как правильно удалять деревья и поддеревья?
Предположим есть табличка:
create table NODES (
ID integer not null,
PARENT_ID integer,
TITLE varchar(254) not null,
MODIFY tymestamp not null,
ORD_NUM integer not null,
constraint PK_NODES primary key (ID),
constraint FK_NODES foreign key (PARENT_ID) references NODES (ID),
);
Одновременно в таблице может находится несколько деревьев.
Как удалять ветку начиная с указанного ID или вовсе очистить всю таблицу?
Если выдать для удаления всего просто
delete from NODES
Он обламается на попытке удаления первого же родителя ещё имеющего детей.
Чуть более сложный запрос удалит только листы:
delete from NODES a
where not exists (select b.ID from NODES b where b.PARENT_ID = a.ID)
И его придётся запускать непонятно сколько раз (не больше максимального
уровня)...
Для удаления листов ветки получается что-то такое:
delete from NODES a
where not exists (select b.ID from NODES b where b.PARENT_ID = a.ID)
and (a.ID = :ID or a.ID in (
with recursive TREE as (
select n.ID, n.PARENT_ID
from NODES n
where n.PARENT_ID = :ID
union all
select n.ID, n.PARENT_ID
from NODES n
inner join TREE t on t.ID = n.PARENT_ID
)
select t.ID
from TREE t
)
Можно ли решить задачку без помощи процедур или EXECUTE BLOCK?
--
Александр Замараев