Mysql
 sql >> база данни >  >> RDS >> Mysql

MySQL:Как да намерите листа в конкретен възел

Няма начин да направите това с една заявка. Дори и да имаше, вероятно би било много неефективно.

Можем да го направим със съхранена процедура и цикъл. С индексите, които добавихте, също трябва да е доста бързо. Това използва две таблици за избор на възлите от входната таблица (A) и вмъкване на възела и техните деца в (B). След това разменя B с A и се повтаря, докато в A не съществуват повече нелистови възли. Хубавото е, че итерациите на цикъл биха били само толкова, колкото са нивата между входния възел и последния листов възел, което в повечето случаи е вероятно не толкова дълбоко. Тази съхранена процедура би била по-бърза, отколкото извършването й външно в код.

За Ваше сведение, имах затруднения с моята инсталация да обработва временни таблици, ако получите „грешка 2“, премахнете временната ключова дума.

delimiter $$
drop procedure if exists GetLeafNodes $$
create procedure GetLeafNodes(nodeid int)
begin
declare N int default 1;

-- create two working sets of IDs, we'll go back and forth between these two sets
drop temporary table if exists A;
drop temporary table if exists B;
create temporary table A(node int, child int);
create temporary table B(node int, child int);

-- insert our single input node into the working set
insert into A values (null, nodeid);

while (N>0) do
  -- keep selecting child nodes for each node we are now tracking
  -- leaf nodes will end up with the child set to null
  insert into B
  select ifnull(A.child,A.node), tree.ID
    from A
    left outer join DATA_TREE as tree on A.child=tree.parent_id;

  -- now swap A and B
  rename table A to temp, B to A, temp to B;

  -- remove non-leaf nodes from table B
  delete from B;

  -- exit when there are no longer any non-leaf nodes in A
  set N=(select count(*) from A where child is not null);
end while;

-- now output our list of leaf nodes
select node from A;

drop temporary table A;
drop temporary table B;
end $$
DELIMITER ;
call GetLeafNodes(4);

Използвах следния набор от примери за тестване:

CREATE TABLE `DATA_TREE` (
  `ID` int(11) NOT NULL,
  `PARENT_ID` int(11) NOT NULL,
  PRIMARY KEY (`ID`),
  UNIQUE KEY `ID_UNIQUE` (`ID`),
  KEY `fk_DATA_TREE_1_idx` (`PARENT_ID`)
) ENGINE=InnoDB
;

insert into DATA_TREE values
(1,0),(2,1),(3,1),(4,1),(5,3),(6,3),(7,4),(8,4),(9,4),(10,6),(11,6),(12,7),(13,9),(14,9),(15,12),(16,12),(17,12),(18,14);



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Как мога да създам инсталатор за уебсайт. PHP mysql

  2. Броят на колоните на mysql.user е грешен. Очаквано 42, намерено 44. Вероятно таблицата е повредена

  3. Емотиконите за iPhone се вмъкват в MySQL, но стават празна стойност

  4. Как да съхранявате географска дължина и ширина в база данни. MySQL няма да отиде по-далеч от -99.9999999

  5. laravel 4 - как да ограничите (вземете и пропуснете) за Eloquent ORM?