繁体   English   中英

SQL多级联接

[英]SQL multi level joins

我需要至少加入4张桌子。 表A是一个关联表,其中包含表B和C的Guid,上级(B),下级(C)。 表D仅包含表C的信息。

我需要结果看起来像这样。

B-C-D

监视器-计算机名-活动

因此,最主要的是显示所有B表,仅显示连接到B的C表,以及仅显示与C相关联的D表。

我怀疑我需要子联接()。 我仍然是一个新手,这在我看来很有意义,但是我似乎无法使代码正常工作。 在过去的两天里,我一直在参加Join。

FROM vHWDesktopMonitor mon             -- [Symantec_CMDB2].[dbo].[ResourceAssociation]
join ResourceAssociation RM on mon._ResourceGuid = RM.ParentResourceGuid 
full outer join vComputer comp on RM.ChildResourceGuid = comp.Guid 
full outer join vAsset on RM.ChildResourceGuid = vAsset._ResourceGuid 

如果我对您的理解正确,那么这两种方法都应该有效”

FROM vHWDesktopMonitor mon             -- [Symantec_CMDB2].[dbo].[ResourceAssociation]
left join ResourceAssociation RM on mon._ResourceGuid = RM.ParentResourceGuid 
left join vComputer comp on RM.ChildResourceGuid = comp.Guid 
left join vAsset on comp.Guid  = vAsset._ResourceGuid 

要么

FROM vHWDesktopMonitor mon             -- [Symantec_CMDB2].[dbo].[ResourceAssociation]
left join ResourceAssociation RM on mon._ResourceGuid = RM.ParentResourceGuid 
left join (select [list fields here] from vComputer comp 
join vAsset on comp.Guid  = vAsset._ResourceGuid) comp2
on RM.ChildResourceGuid = comp2.Guid  

这应该使您获得来自vHWDesktopMonitor的所有记录以及来自ResourceAssociation的关联记录,并且vHWDesktopMonitor中的任何记录都为空,而ResourceAssociation中没有。 然后,您还将在vComputer中获得所有记录,这些记录也在ResourceAssociation中。 最终,您将在vComputer中的vAsset中获得所有记录。 当您要获取第一个表中的所有记录时,请注意,如果您没有关联的记录,则其他表中的字段将为null。

如果这不起作用,也许您需要向我们展示一些示例数据和预期结果。

FROM vHWDesktopMonitor A
FULL OUTER JOIN ResourceAssociation B
  on A._ResourceGuid = B.ParentResourceGuid 
LEFT JOIN vComputer C
  on B.ChildResourceGuid = C.Guid 
LEFT JOIN vAsset D
  on C.ChildResourceGuid = D._ResourceGuid 

所以以上将返回

  • 所有来自A的记录和来自B的所有记录(A,B之间的完整外部)
  • 仅来自C的记录在B中(在B和C之间向左移)
  • 仅来自D的C中的记录(C和D之间的左移)

但是,如果您应用任何where子句限制,则可能会减少由于左或外连接而保留的记录...

例如,如果A._ResourceGuid ='7'在A中存在但在B中不存在; 并在B._ResourceGuid ='7'的位置进行设置,否则将保留A记录,因为将排除完整的外部联接(使完整的外部联接与INNER JOIN相同)!

完整外部将返回如下数据:

A B
7 7
2
  3

如果您添加一个where子句,其中B = 7,那么您可能会因为完整的外部而期望得到,因为您说过要从这两者返回所有记录... AB 7 7 2

但是你最终会得到

A B
7 7

因为where子句出现在完整外部之后,因此减少了A.2记录。 为了弥补这一点,您必须在完全外部执行之前在连接上设置限制,或者在where子句中处理它(但是此方法非常混乱,容易出现错误和性能问题)

因此,当使用外部联接时,您必须将限制条件放在JOIN本身上,如下所示。

FROM vHWDesktopMonitor A
FULL OUTER JOIN ResourceAssociation B
  on A._ResourceGuid = B.ParentResourceGuid 
 and B._resourceGuid = '7'
LEFT JOIN vComputer C
  on B.ChildResourceGuid = C.Guid 
LEFT JOIN vAsset D
  on C.ChildResourceGuid = D._ResourceGuid 

您也可以将其放在where子句中,但必须记住要考虑表上的所有外部联接,并为另一个联接包括null值(这既混乱又缓慢)

FROM vHWDesktopMonitor A
FULL OUTER JOIN ResourceAssociation B
  on A._ResourceGuid = B.ParentResourceGuid 
LEFT JOIN vComputer C
  on B.ChildResourceGuid = C.Guid 
LEFT JOIN vAsset D
  on C.ChildResourceGuid = D._ResourceGuid 
WHERE (A._ResourceGuid is null OR B.ParentResourceGuid ='7')

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM