안녕하세요.
발령이력으로 부서변경이 된 내역만 추출하기 위한 쿼리 문의드립니다.
(기준)발령이력 테이블 샘플
사번 | 부서코드 | 발령코드 | 발령시작일 | 발령종료일 |
1111 | a1234 | AA | 20080101 | 20080321 |
1111 | b1234 | BB | 20080322 | 20091231 |
1111 | b1234 | CC | 20100101 | 20100630 |
1111 | a1234 | AA | 20100701 | 99991231 |
2222 | c1234 | AA | 20091001 | 20101231 |
2222 | c1234 | BB | 20110101 | 99991231 |
(결과)실제 부서변경이 된 경우의 이력
사번 | 부서코드 | 시작일 | 종료일 |
1111 | a1234 | 20080101 | 20080321 |
1111 | b1234 | 20080322 | 20100630 |
1111 | a1234 | 20100701 | 99991231 |
2222 | c1234 | 20091001 | 99991231 |
MSSQL 쿼리로 위와 같은 결과값을 구할 수 있는 좋은 방법이 있을지 문의드립니다.
고수님들 답변 부탁드립니다.
감사합니다.
Comment 2
-
지영아빠
2023.11.07 00:06
-
las****
2023.11.14 17:40
CREATE TABLE #TEMP
(
사번 VARCHAR(4),
부서코드 VARCHAR(5),
발령코드 VARCHAR(2),
시작일 VARCHAR(8),
종료일 VARCHAR(8)
)INSERT INTO #TEMP VALUES('1111','a1234', 'AA', '20080101', '20080321')
INSERT INTO #TEMP VALUES('1111','b1234', 'BB', '20080322', '20091231')
INSERT INTO #TEMP VALUES('1111','b1234', 'CC', '20100101', '20100630')
INSERT INTO #TEMP VALUES('1111','a1234', 'AA', '20100701', '99991231')
INSERT INTO #TEMP VALUES('2222','c1234', 'AA', '20091001', '20101231')
INSERT INTO #TEMP VALUES('2222','c1234', 'BB', '20110101', '99991231')------------------------------------------------------------------------------------
CREATE TABLE #DATA
(
사번 VARCHAR(4),
부서코드 VARCHAR(5),
시작일 VARCHAR(8),
종료일 VARCHAR(8),
CNT INT
)INSERT INTO #DATA
SELECT
A.사번, A.부서코드, A.시작일, A.종료일,
(
SELECT COUNT(*) AS CNNT FROM
(
SELECT 사번 FROM #TEMP
GROUP BY 사번, 부서코드
) D
WHERE A.사번 = D.사번
GROUP BY 사번
) AS CNT
FROM #TEMP ACREATE TABLE #RESULT
(
사번 VARCHAR(4),
부서코드 VARCHAR(5),
시작일 VARCHAR(8),
종료일 VARCHAR(8)
)INSERT INTO #RESULT
SELECT 사번, 부서코드, MIN(시작일), MIN(종료일) FROM #DATA
GROUP BY 사번, 부서코드INSERT INTO #RESULT
SELECT TOP 1 사번, 부서코드, 시작일, 종료일 FROM #DATA
WHERE CNT > 1
ORDER BY 시작일 DESCSELECT * FROM #RESULT
ORDER BY 사번
상황을 이해한 게 아니라 결과에 맞춘 쿼리예요.
case가 달라지면 오류가 생길 것 같으네요.
참고요
with tmp as
(select 1111 as eno, 'a1234' as dno, 'AA' as ano, '20080101' as sdt, '20080321' as edt union all
select 1111 as eno, 'b1234' as dno, 'BB' as ano, '20080322' as sdt, '20091231' as edt union all
select 1111 as eno, 'b1234' as dno, 'CC' as ano, '20100101' as sdt, '20100630' as edt union all
select 1111 as eno, 'a1234' as dno, 'AA' as ano, '20100701' as sdt, '99991231' as edt union all
select 2222 as eno, 'c1234' as dno, 'AA' as ano, '20091001' as sdt, '20101231' as edt union all
select 2222 as eno, 'c1234' as dno, 'BB' as ano, '20110101' as sdt, '99991231' as edt )
select
eno,
dno,
sdt,
edt
from (
select
a.eno,
a.dno,
a.sdt,
isnull(b.edt, a.edt) as edt,
isnull(lag(a.dno) over (order by a.eno, a.sdt), 'x' + a.dno ) as prev_dno
from tmp a
left outer join tmp b
on a.eno = b.eno
and a.dno = b.dno
and convert(varchar(8), case
when a.edt != '99991231' then dateadd(dd, 1, a.edt)
else '99991231' end,
112) = b.sdt
) x
where
dno != prev_dno