MySQL 返回的每一行的子查询循环
MySQL Subquery Looping for each row returned
这使用两个查询,我想获取第一个子查询中返回的每一行的结果,这将 运行 第二个查询,本质上这将像 foreach 循环一样工作。我希望有人能很快解决这个问题。
CREATE TABLE `File_Structure`(
`id` INT PRIMARY KEY AUTO_INCREMENT,
`name` VARCHAR(255) NOT NULL DEFAULT '',
`is_folder` TINYINT(1) NOT NULL DEFAULT 0,
`lft` INT NOT NULL DEFAULT 0,
`rht` INT NOT NULL DEFAULT 0,
`is_active` TINYINT(1) NOT NULL DEFAULT 1,
`created` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
`modified` DATETIME NOT NULL DEFAULT '0000-00-00 00:00:00'
)ENGINE=InnoDB;
INSERT INTO `file_structure` (`id`, `name`, `is_folder`, `lft`, `rht`, `is_active`, `created`, `modified`) VALUES
(1, 'Code', 1, 1, 12, 1, '2017-11-26 00:13:40', '0000-00-00 00:00:00'),
(2, 'Account', 1, 2, 7, 1, '2017-11-26 00:13:40', '0000-00-00 00:00:00'),
(3, 'AccountCreate.php', 0, 3, 4, 1, '2017-11-26 00:13:40', '0000-00-00 00:00:00'),
(4, 'AccountsFindAll.php', 0, 5, 6, 1, '2017-11-26 00:13:40', '0000-00-00 00:00:00'),
(5, 'JournalEntry', 1, 8, 11, 1, '2017-11-26 00:13:41', '0000-00-00 00:00:00'),
(6, 'JournalCreate.php', 0, 9, 10, 1, '2017-11-26 00:13:41', '0000-00-00 00:00:00');
-- 1. FIND ALL LEAF NODES OF A DESIRED NODE.
SELECT `name`
FROM `File_Structure` AS `MAIN`,
(
SELECT `lft`, `rht`
FROM
`File_Structure`
WHERE `name`='Account'
) AS `SUB`
WHERE `MAIN`.`lft`>`SUB`.`lft`
AND `MAIN`.`rht`<`SUB`.`rht`
AND `MAIN`.`rht`=`MAIN`.`lft`+1
;
-- 2. FOR A LEAF NODE, GET A PATH UPTO THE DESIRED NODE.
//SET group_concat_max_len = 2048 TO AVOID THE LIMIT OF 1K STRING LENGTH.
SELECT GROUP_CONCAT(`SUB`.`name` SEPARATOR '/') AS `CONCATEDNAME`
FROM
(
SELECT `PARENT`.`name`
FROM `File_Structure` AS `NODE`,
`File_Structure` AS `PARENT`
WHERE `NODE`.`lft` BETWEEN `PARENT`.`lft` AND `PARENT`.`rht`
AND `NODE`.`name` = 'AccountsFindAll.php'
ORDER BY `PARENT`.`lft`
) AS `SUB`
;
-- 3. REPEAT 2 FOR 1
使用JOIN比各种级别的子查询要容易得多:
SELECT GROUP_CONCAT(path.name ORDER BY path.lft SEPARATOR '/' ) AS CONCATEDNAME
FROM File_Structure AS root
JOIN File_Structure AS leaf ON leaf.lft BETWEEN root.lft AND root.rht
JOIN File_Structure AS path ON leaf.lft BETWEEN path.lft AND path.rht
WHERE leaf.rht = leaf.lft+1
AND root.name='Account'
GROUP BY leaf.name;
输出:
+----------------------------------+
| CONCATEDNAME |
+----------------------------------+
| Code/Account/AccountCreate.php |
| Code/Account/AccountsFindAll.php |
+----------------------------------+
这使用两个查询,我想获取第一个子查询中返回的每一行的结果,这将 运行 第二个查询,本质上这将像 foreach 循环一样工作。我希望有人能很快解决这个问题。
CREATE TABLE `File_Structure`(
`id` INT PRIMARY KEY AUTO_INCREMENT,
`name` VARCHAR(255) NOT NULL DEFAULT '',
`is_folder` TINYINT(1) NOT NULL DEFAULT 0,
`lft` INT NOT NULL DEFAULT 0,
`rht` INT NOT NULL DEFAULT 0,
`is_active` TINYINT(1) NOT NULL DEFAULT 1,
`created` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
`modified` DATETIME NOT NULL DEFAULT '0000-00-00 00:00:00'
)ENGINE=InnoDB;
INSERT INTO `file_structure` (`id`, `name`, `is_folder`, `lft`, `rht`, `is_active`, `created`, `modified`) VALUES
(1, 'Code', 1, 1, 12, 1, '2017-11-26 00:13:40', '0000-00-00 00:00:00'),
(2, 'Account', 1, 2, 7, 1, '2017-11-26 00:13:40', '0000-00-00 00:00:00'),
(3, 'AccountCreate.php', 0, 3, 4, 1, '2017-11-26 00:13:40', '0000-00-00 00:00:00'),
(4, 'AccountsFindAll.php', 0, 5, 6, 1, '2017-11-26 00:13:40', '0000-00-00 00:00:00'),
(5, 'JournalEntry', 1, 8, 11, 1, '2017-11-26 00:13:41', '0000-00-00 00:00:00'),
(6, 'JournalCreate.php', 0, 9, 10, 1, '2017-11-26 00:13:41', '0000-00-00 00:00:00');
-- 1. FIND ALL LEAF NODES OF A DESIRED NODE.
SELECT `name`
FROM `File_Structure` AS `MAIN`,
(
SELECT `lft`, `rht`
FROM
`File_Structure`
WHERE `name`='Account'
) AS `SUB`
WHERE `MAIN`.`lft`>`SUB`.`lft`
AND `MAIN`.`rht`<`SUB`.`rht`
AND `MAIN`.`rht`=`MAIN`.`lft`+1
;
-- 2. FOR A LEAF NODE, GET A PATH UPTO THE DESIRED NODE.
//SET group_concat_max_len = 2048 TO AVOID THE LIMIT OF 1K STRING LENGTH.
SELECT GROUP_CONCAT(`SUB`.`name` SEPARATOR '/') AS `CONCATEDNAME`
FROM
(
SELECT `PARENT`.`name`
FROM `File_Structure` AS `NODE`,
`File_Structure` AS `PARENT`
WHERE `NODE`.`lft` BETWEEN `PARENT`.`lft` AND `PARENT`.`rht`
AND `NODE`.`name` = 'AccountsFindAll.php'
ORDER BY `PARENT`.`lft`
) AS `SUB`
;
-- 3. REPEAT 2 FOR 1
使用JOIN比各种级别的子查询要容易得多:
SELECT GROUP_CONCAT(path.name ORDER BY path.lft SEPARATOR '/' ) AS CONCATEDNAME
FROM File_Structure AS root
JOIN File_Structure AS leaf ON leaf.lft BETWEEN root.lft AND root.rht
JOIN File_Structure AS path ON leaf.lft BETWEEN path.lft AND path.rht
WHERE leaf.rht = leaf.lft+1
AND root.name='Account'
GROUP BY leaf.name;
输出:
+----------------------------------+
| CONCATEDNAME |
+----------------------------------+
| Code/Account/AccountCreate.php |
| Code/Account/AccountsFindAll.php |
+----------------------------------+