我想根据3列过滤我的数据。
示例基础BDD:
id | parent_id | sort | text
-----------------------------
1 | NULL | 3 | D
2 | 10 | 0 | AA
3 | NULL | 1 | B
4 | 10 | 2 | AB
5 | 3 | 0 | BA
6 | 8 | 0 | CA
7 | 3 | 2 | BC
8 | NULL | 2 | C
9 | 3 | 1 | BB
10 | NULL | 0 | A
11 | 1 | 0 | DA
我想得到这个结果:
id | parent_id | sort | text
-----------------------------
10 | NULL | 0 | A
2 | 10 | 0 | AA
4 | 10 | 2 | AB
3 | NULL | 1 | B
5 | 3 | 0 | BA
9 | 3 | 1 | BB
7 | 3 | 2 | BC
8 | NULL | 2 | C
6 | 8 | 0 | CA
1 | NULL | 3 | D
11 | 1 | 0 | DA
我尝试使用COALESCE
功能但未成功:SELECT * FROM menu ORDER BY COALESCE(parent_id, id) ASC, parent_id ASC, sort ASC
。
我认为有COALESCE
函数优先设置订单逻辑......我不确定......
实时测试数据:http://sqlfiddle.com/#!9/ed850/1
解决方案(适用于带有学说的symfony)
感谢@quadzz和其他人的回答
SELECT test.*,
( CASE
WHEN test.parent_id IS NULL THEN test.sort
ELSE test_1.sort
END ) AS test1,
( CASE
WHEN test.parent_id IS NULL THEN 1
ELSE 0
END ) AS test2
FROM test AS test
LEFT JOIN test AS test_1
ON ( test_1.id = test.parent_id )
ORDER BY test1 ASC,
test2 DESC,
test.sort ASC
答案 0 :(得分:1)
应该这样做:
准备数据:
if object_id('tempdb..#t1') is not null drop table #t1
create table #t1
(
id int,
parent_id int,
sort int,
text varchar(10)
)
insert into #t1
values
(1,null,3,'d'),
(2,10,0,'aa'),
(3,null,1,'d'),
(4,10,2,'d'),
(5,3,0,'d'),
(6,8,0,'d'),
(7,3,2,'d'),
(8,null,2,'d'),
(9,3,1,'d'),
(10,null,0,'d'),
(11,1,0,'d')
排序本身:
select *
from #t1 t1
order by
case when t1.parent_id is null then t1.sort
else (
select sort
from #t1 innert1
where innert1.id = t1.parent_id
) end,
case when parent_id is null then 1 end desc,
sort
答案 1 :(得分:0)
我认为这应该有用。
ORDER BY COALESCE(parent_id, id),
case when parent_id is null then 1 else 2 end,
sort
答案 2 :(得分:0)
实际上,您首先需要自行加入到父ID的正确排名顺序。为此,我使用RANK()OVER运行查询,但仅针对您想要的最顶层记录(例如菜单或其他分层组织结构图)的parent_ID = null。
#include <cstring>
#include "MyStrCopy.h"
void MyStrCopy(char* dest, const char* source, int dest_len) {
strncpy(dest, source, dest_len);
dest[dest_len-1] = 0; // zero terminated when source > dest
}
Rank()和order by将返回以下结果
char* MyStrCopy(char* dest, const char* source, int dest_len) {
return strncpy(dest, source, dest_len);
}
现在,您知道所有其他细节需要的最合适的顺序。 现在,在ID =排名ID或父ID =排名ID的情况下,将整个表连接到此结果。所以这样,作为查询基础的所有NULL记录都包含在结果中。
主要排序基于ParentRanked预查询的xRANK列,然后基于此后的正常排序。生成的查询是......
select id, sort, rank() over( order by sort ) as xRank
from YourTable
where parent_id is null