두개의 테이블을 조인해서 보여주는데.. 0 10 2,568

by 볼우물 [SQL Query] [2010.09.16 22:31:49]



A테이블은 코드 테이블입니다. 코드와 코드명이 존재합니다.
B테이블은 코드로 A테이블과 조인해서 보여줄 금액과 일자가 있습니다.

보여줄 결과물은
코드명(CNAME), 전일 금액(AMT), 당일 금액(AMT)
 가     1000   200
 나     500    300
 다     700    100
 라     300    300
이렇게 보여줘야합니다.

문제는 B테이블은 어느 날은 자료가 없어서 코드테이블과 조인해도 모든 코드가 다 나오지 않는겁니다.

A테이블의 구조는 CODE(코드), CNAME(코드명) 이렇게 되고
B테이블의 구조는 DATE(일자), CODE(코드), AMT(금액) 이렇게 됩니다.

두 테이블을 (+) 조인해도 전일과 당일을 받아서 IN 구문을 쓰면 코드가 다 나오지 않습니다.

제가 짠 쿼리는
SELECT A.CODE
    ,SUM(CASE WHEN DATE = '어제일자'
THEN AMT
    ELSE 0
    END) 전일금액
    ,SUM(CASE WHEN DATE = '오늘일자'
THEN AMT
 ELSE 0
    END)  당일금액
FROM A
  ,B
   WHERE A.CODE = B.CODE(+)
    AND B.DATE IN ('어제일자', '오늘일자')
GROUP BY A.CODE

그룹바이 잡지않고 날짜도 하루만 받으면 잘 나오는데
날짜 IN쓰면 안되고 날짜 지워도 그룹바이 잡아도 모든 코드가 다 나오질 않습니다.
도와주세요.
by 知音 [2010.09.17 08:27:53]
:dt1 = 어제날짜, :dt2 = 오늘날짜

[2010-09-17 08:26]

with t1 as (
select 1 cd, '가' nm from dual union all
select 2 cd, '나' nm from dual union all
select 3 cd, '다' nm from dual union all
select 4 cd, '라' nm from dual
), t2 as (
select '20100901' dt, 1 cd, 100 amt from dual union all
select '20100901' dt, 2 cd, 100 amt from dual union all
select '20100902' dt, 1 cd, 100 amt from dual union all
select '20100902' dt, 2 cd, 100 amt from dual union all
select '20100902' dt, 3 cd, 100 amt from dual union all
select '20100902' dt, 4 cd, 100 amt from dual union all
select '20100903' dt, 2 cd, 100 amt from dual union all
select '20100904' dt, 1 cd, 100 amt from dual union all
select '20100904' dt, 4 cd, 100 amt from dual union all
select '20100905' dt, 1 cd, 100 amt from dual union all
select '20100905' dt, 3 cd, 100 amt from dual union all
select '20100905' dt, 4 cd, 100 amt from dual
)
select a.nm
, nvl(b.prv_amt, 0) prv_amt
, nvl(b.cur_amt, 0) cur_amt
from t1 a
, (select cd
, sum(decode(dt, :dt1, amt, 0)) prv_amt
, sum(decode(dt, :dt2, amt, 0)) cur_amt
from t2
where dt >= :dt1
and dt <= :dt2
group by cd
) b
where a.cd = b.cd (+)
order by 1

by 제로 [2010.09.17 09:38:12]
AND B.DATE(+) IN ('어제일자', '오늘일자')

and 조건에도 아우터 조인을 걸어주면 될거 같습니다.

by 知音 [2010.09.17 10:08:36]
[제로]님의 말씀처럼 사용하면

ORA-01719: 포괄 조인 운영 (+)는 OR 또는 IN의 연산수를 허용하지 않습니다

이런 오류가 발생합니다..

양방향 Outer join이 발생하는 셈이 되죠...

by 知音 [2010.09.17 10:11:09]
SELECT A.cd
,SUM(CASE WHEN dt = :dt1
THEN AMT
ELSE 0
END) 전일금액
,SUM(CASE WHEN dt = :dt2
THEN AMT
ELSE 0
END) 당일금액
FROM t1 A
,T2 B
WHERE A.Cd = B.cd(+)
AND B.dt (+) between :dt1 and :dt2
GROUP BY A.cd
order by 1

이렇게 사용하셔도 됩니다.

by 知音 [2010.09.17 10:11:53]
SELECT A.cd
,SUM(CASE WHEN dt = :dt1
THEN AMT
ELSE 0
END) 전일금액
,SUM(CASE WHEN dt = :dt2
THEN AMT
ELSE 0
END) 당일금액
FROM t1 A
,T2 B
WHERE A.Cd = B.cd(+)
AND B.dt (+) >= :dt1
and B.dt (+) <= :dt2
GROUP BY A.cd
order by 1


한가지 더 이렇게 사용하셔도 가능합니다.

by 볼우물 [2010.09.17 10:26:57]
많은 답변 감사합니다. 적용해보겠습니다. 감사합니다. 좋은 하루 되십시오.

by 제로 [2010.09.17 10:37:34]
知音 님 10g에서는 되는거 아닌가요?

by 知音 [2010.09.17 10:57:28]
제가 현재 있는 사이트가 10g 인데 오류가 발생하네요...

by 제로 [2010.09.17 11:09:57]
아~ 10.2.0.4 버젼까지는 에러 발생을 하네요...

현재 저는 10.2.0.5 버젼인데 에러가 발생하지 않네요...

by 知音 [2010.09.17 11:37:15]
아... 그렇군요....

좋은정보 감사합니다..

지금 사이트가 Oracle Database 10g Enterprise Edition Release 10.2.0.4.0 - 64bit 이걸 쓰고 있네요..
댓글등록
SQL문을 포맷에 맞게(깔끔하게) 등록하려면 code() 버튼을 클릭하여 작성 하시면 됩니다.
로그인 사용자만 댓글을 작성 할 수 있습니다. 로그인, 회원가입