如何避免对我的查询使用子查询?

时间:2017-04-16 03:25:10

标签: sql sql-server tsql

我有两个表第一个表GroceryStores看起来像这样

GsName | OrganizationId
-----------------------
'Olymp'| 1
'Carul'| 2
'Caref'| 3
'Viveo'| 2
'Suces'| 4

第二个表组织看起来像这样

Id | Code | ParentOrganizationId
--------------------------------
1  | 'AB' | 0
2  | 'CD' | 3
3  | 'EF' | 4
4  | 'GH' | 0

GroceryStores.OrganizationId和Organizations.Id是相同的。

该查询应该返回与给定的OrganizationId及其各自的ParentOrganization匹配的所有GsName。

我已经尝试过这个查询,但它只适用于GroceryStore只属于一个组织但一个GroceryStore可以有一个ParentOrganization和一个GrandparentOrganization,而不同的GroceryStores可以属于同一个组织。此外,一个GroceryStore可以属于一个组织,该组织可能没有ParentOrganization

SELECT GsName
FROM GroceryStores INNER JOIN Organizations
ON ParentOrganizationId = Id
WHERE OrganizationId = @Organization
OR WHERE OrganizationId = (SELECT ParentOrganizationId FROM Organizations 
WHERE Id = @Organization) 

3 个答案:

答案 0 :(得分:0)

为什么不尝试,IN代替EQUAL,当你说EQUAL时你必须确保SUBQUERY只返回1行,如果你希望在查询中使用LIMIT 1,你可以这样做

    SELECT GsName
    FROM GroceryStores INNER JOIN Organizations
    ON ParentOrganizationId = Id
    WHERE OrganizationId = @Organization
    OR WHERE OrganizationId IN (SELECT ParentOrganizationId FROM Organizations 
    WHERE Id = @Organization) 

答案 1 :(得分:0)

由于您需要遍历父层次结构,因此请使用recursive CTE,如下所示:

WITH Org
AS
(
    SELECT Id,ParentOrganizationId 
    FROM Organizations
    WHERE Id = @Org
    UNION ALL
    SELECT O.Id,O.ParentOrganizationId
    FROM Org O1
    INNER JOIN Oranizations O
    ON O1.ParentOrganizationId = O.Id
)
SELECT GsName 
FROM GroceryStores
WHERE OrganizationId IN
(
    SELECT Id FROM Org
)

答案 2 :(得分:0)

为防止您的查询在执行期间失败,请将查询更改为此, 请注意,我已将=替换为IN

SELECT GsName
FROM GroceryStores INNER JOIN Organizations
ON ParentOrganizationId = Id
WHERE OrganizationId = @Organization
OR WHERE OrganizationId IN (SELECT ParentOrganizationId FROM Organizations 
WHERE Id = @Organization)