通过外部连接Oracle 11i中的两个表来消除重复行

时间:2014-08-20 11:03:35

标签: sql oracle

我有两张带有样本数据的表格。

  

PLACED_PERSON_INFO

         *PLACED_PERSON_INFO_GUID                 CPR*
                 P1                           0201026157
                 P2                           0309929493
                 P3                           0002170000
                 P4                           0000011037
                 P5                           1201006694
                 P6                           1201009887
                 P7                           1110007144
                 P8                           0309906353
                 P9                           0101002420

PLACED_PERSON_PLACES

 *PP_ID   PLACEMENT_DATE         PLACEMENT_STOP    PLACED_PERSON_INFO_GUID*
   1       01-01-2014              31-12-2014              P1
   2       01-01-2014              31-12-2014              P1
   3       01-01-2013              31-12-2013              P2
   4       01-06-2014              30-10-2014              P3
   5       01-02-2014              30-10-2014              P3
   6       01-01-2013              01-01-2015              P4
   7       01-01-2013              30-05-2013              P4
   8       01-01-2012              30-03-2013              P5

我编写了以下SQL Query来获取组合这两个表的结果。

SQL查询:

SELECT
PPI.PLACED_PERSON_INFO_GUID, PPI.CPR
FROM PLACED_PERSON_PLACES PPP, PLACED_PERSON_INFO PPI
WHERE (PPP.PLACEMENT_DATE <= SYSDATE OR PPP.PLACEMENT_DATE IS NULL)
AND (PPP.PLACEMENT_STOP >= SYSDATE OR PPP.PLACEMENT_STOP IS NULL)
AND PPP.PLACED_PERSON_INFO_GUID (+) = PPI.PLACED_PERSON_INFO_GUID
ORDER BY PPI.CPR;

查询结果:

        PLACED_PERSON_INFO_GUID             CPR
              P1                          0201026157
              P1                          0201026157
              P3                          0002170000
              P3                          0002170000
              P4                          0000011037
              P6                          1201009887
              P7                          1110007144
              P8                          0309906353
              P9                          0101002420

但我想要以下结果,其中不会显示重复的行。我不想使用 DISTINCT 关键字 。任何人都可以帮我这个结果吗?我正在使用Oracle 11i。

预期结果:

               PLACED_PERSON_INFO_GUID              CPR
                        P1                      0201026157
                        P3                      0002170000
                        P4                      0000011037
                        P6                      1201009887
                        P7                      1110007144
                        P8                      0309906353
                        P9                      0101002420

2 个答案:

答案 0 :(得分:1)

首先,您应该使用显式join语法编写查询:

SELECT PPI.PLACED_PERSON_INFO_GUID, PPI.CPR
FROM PLACED_PERSON_INFO PPI LEFT JOIN
     PLACED_PERSON_PLACES PPP
     ON PPP.PLACEMENT_DATE <= SYSDATE AND 
        PPP.PLACEMENT_STOP >= SYSDATE AND
        PPP.PLACED_PERSON_INFO_GUID = PPI.PLACED_PERSON_INFO_GUID
ORDER BY PPI.CPR;

如果您只需要一行,则可以使用row_number()

SELECT PLACED_PERSON_INFO_GUID, CPR
FROM (SELECT PPI.PLACED_PERSON_INFO_GUID, PPI.CPR,
             ROW_NUMBER() OVER (PARTITION BY PPI.PLACED_PERSON_INFO_GUID, PPI.CPR ORDER BY PPI.CPR) as seqnum
      FROM PLACED_PERSON_INFO PPI LEFT JOIN
           PLACED_PERSON_PLACES PPP
           ON PPP.PLACEMENT_DATE <= SYSDATE AND 
              PPP.PLACEMENT_STOP >= SYSDATE AND
              PPP.PLACED_PERSON_INFO_GUID = PPI.PLACED_PERSON_INFO_GUID
     ) p
WHERE seqnum = 1;
ORDER BY CPR;

您可以添加其他列,但每对只能获得一行。

答案 1 :(得分:0)

解决方案是:

SELECT PLACED_PERSON_INFO_GUID, CPR
FROM (SELECT PPI.PLACED_PERSON_INFO_GUID, PPI.CPR,
      ROW_NUMBER() OVER (PARTITION BY PPI.PLACED_PERSON_INFO_GUID, PPI.CPR ORDER BY PPI.CPR) AS SEQNUM
      FROM PLACED_PERSON_INFO PPI LEFT JOIN PLACED_PERSON_PLACES PPP
      ON PPP.PLACED_PERSON_INFO_GUID = PPI.PLACED_PERSON_INFO_GUID                
      WHERE (PPP.PLACEMENT_DATE <= SYSDATE OR PPP.PLACEMENT_DATE IS NULL)
      AND (PPP.PLACEMENT_STOP >= SYSDATE OR PPP.PLACEMENT_STOP IS NULL)
     ) P
WHERE SEQNUM = 1
ORDER BY CPR