我目前有这个我写的sql语句,但是它有效,但它不是我想要的。我已经工作了几个小时但似乎无法再进一步了。
select parent.id as parent_id, parent.subject as parent,s.id,s.subject from (select s.id, s.subject from subjects s where parent_id = 0) parent join subjects s on parent.id = s.parent_id order by parent.subject, s.subject
它正在抓取所有主题并正确排序,但我也希望在每个分组的顶部返回父主题(parent_id = 0)。这是因为有些父母可能没有下面的主题,但我仍然需要退回它们。当我尝试这样做时,排序也是关闭的,因为我首先想要父母,然后是孩子的主题。希望这是有道理的,但如果不是只是问。
任何帮助都将不胜感激。
由于
史蒂夫
答案 0 :(得分:0)
您所说的是按父行分组行集。
我知道如何在MySQL中执行此操作的唯一方法是使用GROUP_CONCAT()
函数,该函数不会按行对主题进行分组,而是创建分组字符串。
以下是您可以做的事情:
SELECT
a.id,
a.subject,
GROUP_CONCAT(CONCAT(b.id, ':::', b.subject) ORDER BY b.subject SEPARATOR '|||') AS subjectlist
FROM
subjects a
LEFT JOIN
subjects b ON a.id = b.parent_id
WHERE
a.parent_id = 0
GROUP BY
a.id,
a.subject
ORDER BY
a.subject
因此,这将为您提供如下结果集:
id | subject | subjectlist
---------------------------------------------------------------------
2 | subj1 | 23:::childsubj1|||28:::childsubj4
3 | subj2 | 18:::childsubj8|||55:::childsubj16
4 | subj3 | NULL
根据您在应用程序中使用的语言,您可以“爆炸”将subjects
字符串放入由|||
分隔的数组中,这些数组将每个主题分开,然后:::
分隔该主题的ID和名称。
显然,这样做的缺点是你必须确保你的孩子主题名称不包含|||
或:::
或你决定使用的任何分隔符。
编辑:在实验上,我想出了这个可能更接近您所寻找的替代解决方案:
尝试:
SELECT
c.subj,
c.id
FROM
(
SELECT
CONCAT('---> ', b.subject) AS subj,
b.id,
CONCAT(a.subject, b.subject) AS orderfactor
FROM
subjects a
INNER JOIN
subjects b ON a.id = b.parent_id
WHERE
a.parent_id = 0
UNION ALL
SELECT
subject AS subj,
id,
subject AS orderfactor
FROM
subjects
WHERE
parent_id = 0
) c
ORDER BY
c.orderfactor
此查询应该为您提供以下行的结果:
subject | id |
----------------------------------------------------------
subj1 | 2 |
---> childsubj1 | 23 |
---> childsubj4 | 28 |
subj2 | 3 |
---> childsubj8 | 18 |
---> childsubj16 | 55 |
subj3 | 4 |
subj4 | 5 |
---> childsubj10 | 79 |