我已经制作了一个简单的表来理解亲子关系,但我似乎没有得到正确的结果。我想对它进行排序
示例表:
=============================================== =============
CREATE TABLE IF NOT EXISTS `test` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`parent_id` int(11) NOT NULL DEFAULT '0',
`name` varchar(255) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=9 ;
--
-- Dumping data for table `test`
--
INSERT INTO `test` (`id`, `parent_id`, `name`) VALUES
(1, 4, 'Zorg'),
(2, 0, 'Woordolack'),
(3, 4, 'Akriller'),
(4, 0, 'Metabrusher'),
(5, 2, 'Intersplitter'),
(6, 0, 'Beaverbrain'),
(7, 4, 'Torgeoruos'),
(8, 2, 'Deptezaurus');
=============================================== =============
Beaverbrain
Metabrusher
-> Akriller
-> Torgeoruos
-> Zorg
Woordolack
-> Deptezaurus
-> Intersplitter
=============================================== =============
我应该说这是一个示例表来展示这个想法,所以可以通过任何方式修改它以获得正确的结果。
答案 0 :(得分:3)
您可以尝试此查询
SELECT IF(child = '',parent,CONCAT('->',child)) as value
FROM
(SELECT parent.name as parent,child.name as child
FROM test parent
INNER JOIN
(SELECT id,parent_id,name FROM test
UNION
SELECT null,id,'' FROM test
WHERE parent_id = 0)child
WHERE parent.parent_id = 0
AND child.parent_id = parent.id
ORDER BY parent,child
)parent_child
查询的作用是INNER JOIN test with test并找出哪个是父级和子级。内部UNION SELECT null,id,'' FROM test WHERE parent_id = 0
创建一个空子(ren)用于显示目的。然后,外部SELECT看到孩子是否''它打印出父母,否则它在孩子面前结束->
。所以你得到的结果就像你想要的那样。
以下版本可能会快一点。因为我们只是使用NULL子节点创建父节点而不是使用子节点作为INNER JOIN的一部分(上图)。
SELECT IF(child IS NULL,parent,CONCAT('->',child)) as value
FROM
(SELECT parent.name as parent,child.name as child
FROM test parent
INNER JOIN test child ON child.parent_id = parent.id
WHERE parent.parent_id = 0
UNION
SELECT test.name as parent,NULL as child #This creates a NULL child row
FROM test WHERE test.parent_id = 0 #for parent display purpose
ORDER BY parent,child
)parent_child
然而,我会在PHP中使用以下查询,检查isParent
标志是1还是0,然后显示相应的字段。
SELECT 0 as isParent,parent.name as parent,child.name as child,
parent.id as parentId,child.id as childId
FROM test parent
INNER JOIN test child ON child.parent_id = parent.id
WHERE parent.parent_id = 0
UNION
SELECT 1 as isParent,test.name as parent,NULL as child,
test.id as parentId,NULL as childId
FROM test WHERE test.parent_id = 0
ORDER BY parent,child
答案 1 :(得分:0)
在管理分层数据时,您可以使用简单的PHP递归函数,
function DisplayTree( $parent , $depth) {
$sql = $this->db->query("SELECT id,name FROM '$table' WHERE parent_id = '$parent'");
foreach($sql->result() as $field ) {
print "<fieldset style=\"margin-left:$depth%; width:300px\">";
print $field->name;
print "</fieldset>";
$this->DisplayTree( $field->code , $depth+8 );
}
}
答案 2 :(得分:0)
在PHP中使用几个简单的查询,
$r1 = $db->query("select * from test where parent_id = 0 order by name asc") or die('err in q1');
while($arr1 = $r1->fetch_assoc()){
$parent = $arr1['name'];
$parent_id = $arr1['id'];
echo $parent
$r2 = $db->query("select * from test where parent_id = $parent order by name asc") or die('err in q2');
while($arr2 = $r2->fetch_assoc()){
$child = $arr2['name'];
echo $child."<br />";
}
}
答案 3 :(得分:0)
试试这个解决方案:
SELECT
A.id,
A.name
FROM
`test` AS A LEFT JOIN `test` AS B ON A.`parent_id` = B.`id`
GROUP BY
A.`id`
ORDER BY
IFNULL(B.`name`, A.`name`),
COALESCE(A.`parent_id`, A.`id`),
A.`parent_id` != 0,
A.`name`;