mysql - 嵌套 SELECT + INNER JOIN

标签 mysql nested normalization

第一个表

  CREATE TABLE IF NOT EXISTS `city_node` (
 `node_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
 `title` varchar(50) NOT NULL,
 `parent_node_id` int(10) unsigned NOT NULL DEFAULT '0',
 `lft` int(10) unsigned NOT NULL DEFAULT '0' COMMENT 'Nested set info ''left'' value',
 `rgt` int(10) unsigned NOT NULL DEFAULT '0' COMMENT 'Nested set info ''right'' value',
 `depth` int(10) unsigned NOT NULL DEFAULT '0' COMMENT 'Depth = 0: no parent',
 PRIMARY KEY (`node_id`),
 KEY `parent_node_id` (`parent_node_id`),
 KEY `lft` (`lft`)) ENGINE=InnoDB  DEFAULT CHARSET=utf8 AUTO_INCREMENT=26;

和数据

INSERT INTO `city_node` (`node_id`, `title`, `parent_node_id`, `lft`, `rgt`, `depth`) VALUES
(1, 'Great Britain', 0, 1, 20, 0),
(3, 'England', 1, 2, 9, 1),
(7, 'Scotland', 1, 16, 19, 1),
(8, 'Edinburgh', 7, 17, 18, 2),
(9, 'Wales', 1, 10, 15, 1),
(10, 'Cardiff', 9, 11, 12, 2),
(11, 'London', 3, 3, 4, 2),
(12, 'Birmingham', 3, 5, 6, 2),
(13, 'Germany', 0, 21, 26, 0),
(14, 'Stuttgart', 13, 22, 23, 1),
(15, 'Newport', 9, 13, 14, 2),
(16, 'Munich', 13, 24, 25, 1),
(17, 'Israel', 0, 27, 32, 0),
(18, 'Tel Aviv', 17, 28, 29, 1),
(19, 'Ashdod', 17, 30, 31, 1),
(20, 'USA', 0, 33, 38, 0),
(21, 'New York', 20, 34, 35, 1),
(24, 'Liverpool', 3, 7, 8, 2),
(25, 'Detroit', 20, 36, 37, 1);

第二个表

CREATE TABLE IF NOT EXISTS `city_node_entity` (
  `node_id` int(10) NOT NULL,
  `entity` tinyint(3) unsigned NOT NULL DEFAULT '1',
  KEY `node_id` (`node_id`,`entity`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

和数据

INSERT INTO `city_node_entity` (`node_id`, `entity`) VALUES
(11, 1),
(12, 1),
(16, 1),
(19, 1);

我想获取具有实体 1 及其祖先的节点,如下所示

英国
--英格兰
----伦敦
----伯明翰
德国
--慕尼黑 以色列
——阿什杜德

所以,我的查询是

SELECT DISTINCT(node_ext.node_id), node_ext.*
FROM city_node_entity AS entity
LEFT JOIN city_node AS node 
    ON entity.node_id = node.node_id 
LEFT JOIN city_node AS node_ext 
    ON node_ext.lft <= node.lft AND node_ext.rgt >= node.rgt
WHERE entity.entity = 1
ORDER BY node_ext.lft

但解释显示 -使用地点;使用索引;使用临时的;使用文件排序

是否有任何其他查询可以获得相同的结果,但[额外]更少?

最佳答案

对于递归查询,您唯一可以做的就是使用每个父/子的联接来运行它......因为您的第二个表是实际的城市名称,并且您想要向后工作,您可以这样做...... .只需添加更多连接,直到所有结果都为空,您将拥有完整的树

SELECT node.title AS child, t2.title as parent1, t3.title as parent2, t4.title as parent3
FROM city_node_entity AS entity
LEFT JOIN city_node AS node ON entity.node_id = node.node_id 
LEFT JOIN city_node AS t2 ON t2.node_id = node.parent_node_id
LEFT JOIN city_node AS t3 ON t3.node_id = t2.parent_node_id
LEFT JOIN city_node AS t4 ON t4.node_id = t3.parent_node_id;

Fiddle Demo

关于mysql - 嵌套 SELECT + INNER JOIN,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26221638/

相关文章:

csv - 特征缩放/归一化中的最小值和最大值?

php - 通过php准备语句插入mySql失败

mysql - 未找到 CWP 数据库

php - 函数中的 CodeIgniter "Using $this when not in object context"

Javascript 无限嵌套数组处理

c - C 中的嵌套 for 循环

TEXT 列上的 MySQL 索引无效

javascript - 嵌套的 Javascript 模板……这可能/有效吗?

string - 何时使用 Unicode 规范化形式 NFC 和 NFD?

python - 如何使用 python 规范化原始音频文件