SQL Server选择从另一个表获取单行

时间:2014-03-24 13:49:24

标签: sql sql-server-2008

这里需要一些SQL Server选择查询的帮助。

我定义了以下表格:

UserSource

UserSourceID ID Name Dept SourceID
1            1  John AAAA 1
2            1  John AAAA 2
3            2  Nena BBBB 1
4            2  Nena BBBB 2
5            3  Gord AAAA 2
6            3  Gord AAAA 1
7            4  Stan CCCC 3

来源

SourceID Description RankOrder
1        FromHR      1
2        FromTemp    2
3        Others      3

需要连接两个表并仅选择排名最小的行。这样得到的行将是:

UserSourceID ID Name Dept SourceID Description RankOrder
1            1  John AAAA 1        FromHR      1
3            2  Nena BBBB 1        FromHR      1
6            3  Gord AAAA 1        FromHR      1
7            4  Stan CCCC 3        Others      3

TIA。

编辑:

这是我到目前为止所得到的,但我似乎错过了一些东西:

WITH
TableA AS(
SELECT 1 AS UserSourceID, 1 AS ID, 'John' AS [Name], 'AAAA' as [Dept], 1 as SourceID
UNION SELECT 2, 1, 'John', 'AAAA', 2
UNION SELECT 3, 2, 'Nena', 'BBBB', 1
UNION SELECT 4, 2, 'Nena', 'BBBB', 2
UNION SELECT 5, 3, 'Gord', 'AAAA', 2
UNION SELECT 6, 3, 'Gord', 'AAAA', 1
UNION SELECT 7, 4, 'Stan', 'DDDD', 3)
,
TableB AS(
SELECT 1 as SourceID, 'FromHR' as [Description], 1 as RankOrder
UNION SELECT 2, 'FromTemp', 2
UNION SELECT 3, 'Others', 3
)

SELECT DISTINCT tblA.*, tblB.SourceID, tblB.Description
FROM TableB tblB
JOIN TableA tblA ON tblA.SourceID = tblB.SourceID
LEFT JOIN TableB b2 ON b2.SourceID = tblB.SourceID
AND B2.RankOrder < tblB.RankOrder
WHERE B2.SourceID IS NULL

更新: 我扫描了表格,可能会有一些数据变化。我已经更新了上述问题的数据。

实际上,我需要加入这两个表,并且只能选择RankOrder最少的行。在记录UserSourceID = 7的情况下,将选择该特定记录,因为在加入表之后只存在一行。

1 个答案:

答案 0 :(得分:2)

我经常使用窗口聚合来处理这种类型的解决方案。 ROW_NUMBER会根据您在PARTITION子句中指定的ORDEROVER对行进行排序和编号。

select  UserSoruceID
        , ID
        , Name
        , Dept
        , SourceID
        , Description
        , RankOrder
FROM    (SELECT  UserSoruceID
                , ID
                , Name
                , Dept
                , u.SourceID
                , Description
                , RankOrder
                , ROW_NUMBER() over(PARTITION BY ID ORDER BY RankOrder) ranknum
        FROM    UserSource u
         INNER JOIN
                Source s
               on s.SourceID = u.SourceID ) a
WHERE   ranknum = 1

因此,在这种情况下,对于每个ID,根据RankOrder对行进行编号,然后对其进行过滤,以便您只查看第一行。

这是Microsoft提供的有关该功能的有用链接。 ROW_NUMBER

---- ---- UPDATE

这里有排名和行号作为选项。

select  UserSoruceID
        , ID
        , Name
        , Dept
        , SourceID
        , Description
        , RankOrder
FROM    (SELECT  UserSoruceID
                , ID
                , Name
                , Dept
                , u.SourceID
                , Description
                , RankOrder
                , ROW_NUMBER() over(PARTITION BY ID ORDER BY RankOrder) row_num
                , RANK() over(PARTITION BY ID ORDER BY RankOrder) rank_num --use this if you want to see the duplicate records
        FROM    UserSource u
         INNER JOIN
                Source s
               on s.SourceID = u.SourceID ) a
WHERE   row_num = 1 --rank_num = 1

将row_num替换为rank_num以查看具有重复RankOrder条目的任何项目