使用 CTE 比较多行数据

Using CTE for comparing data in multiple rows

在这个数据集中,我需要标记出应用程序 ID P-10900,因为它被 2 个 TeamMember 触及。 我们可以以创建为单独列的标志的形式将其标记出来。

我知道可以使用递归 CTE 轻松完成,但不确定如何编写语法。

TeamMember      Status      ApplicationID
NULL            NW          P-10900
John            IR          P-10900
John            CO          P-10900
Dick            IR          P-10900
Dick            PA          P-10900
NULL            NW          P-06700
John            IR          P-06700
John            PA          P-06700
NULL            NW          P-14600
Andre           IR          P-14600

这是对此处提出的问题的扩展

Find which rows have different values for a given column in SQL

我正在使用 MS SQL Server 2012

我期待这样的输出:

TeamMember        Status        ApplicationID   Flag
NULL              NW            P-10900         Dup
John              IR            P-10900         Dup
John              CO            P-10900         Dup
Dick              IR            P-10900         Dup
Dick              PA            P-10900         Dup
NULL              NW            P-06700         Alike   
John              IR            P-06700         Alike
John              PA            P-06700         Alike
NULL              NW            P-14600         Alike
Andre             IR            P-14600         Alike

这是架构:

CREATE TABLE App
    ([TeamMember] varchar(5), [aStatus] varchar(2), [ApplicationID] varchar(7))
;

INSERT INTO App
    ([TeamMember], [aStatus], [ApplicationID])
VALUES
    (NULL, 'NW', 'P-10900'),
    ('John', 'IR', 'P-10900'),
    ('John', 'CO', 'P-10900'),
    ('Dick', 'IR', 'P-10900'),
    ('Dick', 'PA', 'P-10900'),
    (NULL, 'NW', 'P-06700'),
    ('John', 'IR', 'P-06700'),
    ('John', 'PA', 'P-06700'),
    (NULL, 'NW', 'P-14600'),
    ('Andre', 'IR', 'P-14600')
;

这是我尝试过的方法,当然是行不通的:

 WITH cte (applicationid, status, teammember)
     AS (SELECT applicationid,
                status,
                teammember
         FROM   app
         GROUP  BY applicationid,
                   status,
                   teammember)
SELECT applicationid,
       teammember,
       status,
       CASE
         WHEN (SELECT DISTINCT CASE
                                 WHEN Count(applicationid) > 1 THEN 'Alike'
                                 ELSE 'Dup'
                               END
               FROM   cte B
               WHERE  B.teammember = A.teammember
               GROUP  BY B.teammember) = 'Alike' THEN 'Alike'
         ELSE 'Dup'
       END AS Flag
FROM   cte A
ORDER  BY applicationid  

你只是把事情复杂化了。您在这里根本不需要 CTE:

SELECT a.*, dups.Flag
FROM app a INNER JOIN (
    SELECT ApplicationID, CASE
          WHEN MIN(TeamMember) = MAX(TeamMember) THEN 'Alike'
          ELSE 'Dup'
        END Flag
    FROM app t
    GROUP BY ApplicationID) dups
  ON a.ApplicationID = dups.ApplicationID