从SQL中的子记录派生父记录
我有如下数据,如下所示 桌子 我需要以这样一种方式输出数据:我可以在一个单独的行中显示父记录,该行基于标识符链接2个子id 预期结果:从SQL中的子记录派生父记录,sql,sql-server,database,left-join,Sql,Sql Server,Database,Left Join,我有如下数据,如下所示 桌子 我需要以这样一种方式输出数据:我可以在一个单独的行中显示父记录,该行基于标识符链接2个子id 预期结果: +----+-----------+---------+----------+------------+ | ID | Parent_ID | Child_1 | Child_2 | Identifier | +----+-----------+---------+----------+------------+ | C1 | P1 | NULL
+----+-----------+---------+----------+------------+
| ID | Parent_ID | Child_1 | Child_2 | Identifier |
+----+-----------+---------+----------+------------+
| C1 | P1 | NULL | NULL | IN |
| C2 | P1 | NULL | NULL | OUT |
| P1 | NULL | C1 | C2 | IN |
| C1 | P2 | NULL | NULL | IN |
| C2 | P2 | NULL | NULL | OUT |
| P2 | NULL | C1 | C2 | IN |
+----+-----------+---------+----------+------------+
为了实现这一点,我运行了下面的查询,其中我尝试离开join以分离父记录,然后使用UNION来查找子记录
-- Parent
Select c1.PARENT_ID as ID,
Parent_Id,
c1.Child_ID as Child_1
c2.Child_ID as Child_2
c1.Identifier
from sampletable as c1
left join sampletable as c2
on c2.PARENT_ID = c1.PARENT_ID
and c2.Identifier = 'OUT'
where c1.Identifier = 'IN'
UNION
-- CHILD
Select child_id as ID,
Parent_id,
CASE when Identifier = 'IN' then Child_ID
Else NULL END As Child_1,
CASE when Identifier = 'OUT' then Child_ID
Else NULL END As Child_2,
Identifier
from sampletable
where parent_id is not null
请有人指出我做错了什么 按原样选择孩子 对于父项,使用来自的
中的子查询,以获取一组不同的父项ID
s。假设只有两个子查询,您可以在列列表中使用其他子查询,分别选择min(Child\u ID)
或max(Child\u ID)
UNION ALL
两个结果
将一个外部查询放在UNION ALL
的结果上,并按coalesce(Parent_ID,ID)对其排序,如果ID为NULL,则为1,否则为0 END,ID
,以实现所需的顺序。CASE
是一种确保ID
s为NULL
的黑客攻击。(我不确定NULLS
在SQL Server中是第一位还是最后一位,现在懒得查找它。或者如果我没记错的话,还有一个数据库范围的选项?无论如何,在查询中显式地使用它是最安全的选择。)
-- Parent
Select c1.PARENT_ID as ID,
Parent_Id,
c1.Child_ID as Child_1
c2.Child_ID as Child_2
c1.Identifier
from sampletable as c1
left join sampletable as c2
on c2.PARENT_ID = c1.PARENT_ID
and c2.Identifier = 'OUT'
where c1.Identifier = 'IN'
UNION
-- CHILD
Select child_id as ID,
Parent_id,
CASE when Identifier = 'IN' then Child_ID
Else NULL END As Child_1,
CASE when Identifier = 'OUT' then Child_ID
Else NULL END As Child_2,
Identifier
from sampletable
where parent_id is not null
SELECT *
FROM (SELECT Child_ID ID,
Parent_ID,
NULL Child_1,
NULL Child_2,
Identifier
FROM sampletable
UNION ALL
SELECT x.Parent_ID ID,
NULL Parent_ID,
(SELECT min(Child_ID)
FROM sampletable y
WHERE y.Parent_ID = y.Parent_ID) Child_1,
(SELECT max(Child_ID)
FROM sampletable y
WHERE y.Parent_ID = y.Parent_ID) Child_2,
'IN' Identifier
FROM (SELECT DISTINCT Parent_ID
FROM sampletable) x) u
ORDER BY coalesce(Parent_ID,
ID),
CASE
WHEN ID IS NULL
THEN 1
ELSE
0
END,
ID;