9-2-1. INLINE VIEW와 JOIN


인라인 뷰에서 데이터를 GROUP BY 처리한 후에 조인을 할 수도 있다. 아래 SQL은 Ord 테이블을 인라인 뷰(T2)에서 ShopId로 GROUP BY 한 후에 조인을 하고 있다. 이와 같은 패턴은 조인을 조금 더 이해하기 쉽게 만들어주기도 한다.

-- [SQL-9-2-1-a] 인라인 뷰에서 GROUP BY 후 조인 처리
SELECT  T1.ShopId
        ,T1.ShopNm ShopNm
        ,IFNULL(T2.OrdAmt,0) OrdAmt
FROM    startdb.Shop T1
        LEFT OUTER JOIN (
            SELECT  A.ShopID ,SUM(A.OrdAmt) OrdAmt
            FROM    startdb.Ord A
            WHERE   A.OrdDtm >= STR_TO_DATE('20220101','%Y%m%d')
            AND     A.OrdDtm <  STR_TO_DATE('20220201','%Y%m%d')
            GROUP BY A.ShopId
            ) T2
                ON (T2.ShopId = T1.ShopId)
WHERE   T1.ShopStartYmd = '20180327'
AND     T1.ShopOperTp = 'FLAG'
ORDER BY T1.ShopID;

ShopId  ShopNm        OrdAmt     
------  ------------  ---------  
S014    Columbus-1st  68500.000  
S031    Austin-2nd    37500.000  

9-2-2. 1:M 조인 후 1쪽 Key로 GROUP BY 패턴


2018년 3월 27일에 개점한 매장의 매장별 2019년 10월 주문금액을 구하려고 한다. 아래와 같이 조인 후 GROUP BY를 처리해 원하는 결과를 구할 수 있다.

-- [SQL-9-2-2-a] 1:M(Shop:Ord) 조인 후 GROUP BY
-- 20180327에 개점한 매장의 2019년 10월 주문금액
SELECT  T1.ShopId
        ,MAX(T1.ShopNm) ShopNm
        ,IFNULL(SUM(T2.OrdAmt),0) OrdAmt
FROM    startdb.Shop T1
        LEFT OUTER JOIN startdb.Ord T2
            ON (T2.ShopID = T1.ShopId
                AND T2.OrdDtm >= STR_TO_DATE('20191001','%Y%m%d')
                AND T2.OrdDtm <  STR_TO_DATE('20191101','%Y%m%d'))
WHERE   T1.ShopStartYmd = '20180327'
GROUP BY T1.ShopID
ORDER BY T1.ShopID;

ShopId  ShopNm         OrdAmt     
------  -------------  ---------  
S014    Columbus-1st   23000.000  
S028    San Diego-2nd  8000.000   
S031    Austin-2nd     0.000      

위 SQL은 아래 그림과 같은 과정으로 최종 데이터 집합이 만들어진다. Shop과 Ord는 1:M 관계다. 그러므로 Shop은 M쪽인 Ord만큼 데이터가 늘어났다가, GROUP BY로 인해 다시 Shop쪽 만큼 데이터가 줄어들게 된다.

image.png

이와 같은 SQL 패턴을 “1:M 조인 후 1쪽 Key로 GROUP BY” 패턴이라고 부르도록 하자.

9-2-3. 인라인 뷰를 활용한 1:1 조인 패턴

“1:M 조인 후 1쪽 Key로 GROUP BY 패턴”은 “인라인 뷰를 활용해 1:1 조인”으로 변경해서 처리할 수도 이다. 위에서 살펴본 SQL은 아래와 같은 패턴으로 변경해 볼 수 있다.

-- [SQL-9-2-3-a] 인라인 뷰로 1:1 조인
-- Ord를 인라인 뷰에서 GROUP BY 처리후 조인하는 SQL
-- Shop과 인라인 뷰는 1:1로 조인이 이루어진다.
SELECT  T1.ShopId
        ,T1.ShopNm ShopNm
        ,IFNULL(T2.OrdAmt,0) OrdAmt
FROM    startdb.Shop T1
        LEFT OUTER JOIN (
            SELECT  A.ShopID ,SUM(A.OrdAmt) OrdAmt
            FROM    startdb.Ord A
            WHERE   A.OrdDtm >= STR_TO_DATE('20191001','%Y%m%d')
            AND     A.OrdDtm <  STR_TO_DATE('20191101','%Y%m%d')
            GROUP BY A.ShopId
            ) T2
                ON (T2.ShopId = T1.ShopId)
WHERE   T1.ShopStartYmd = '20180327'
ORDER BY T1.ShopID;