http://www.soqool.com/servlet/board?cmd=view&cat=100&subcat=1010&seq=102&page=1&position=1SoQool에서 퍼왔어요..
글쓴이 : 김홍선
예제 1)
다음과 같은 문자열이 있다.
123,11,4567,8,99999,000,123456
이 문자열을 콤마(,)를 기준으로 행으로 분리해 보자. 즉 아래와 같은 결과가 나오도록 해보자.
123
11
4567
...
...
쿼리는 다음과 같다.
SELECT SUBSTR (aa,
INSTR (aa, ',', 1, LEVEL) + 1,
INSTR (aa, ',', 1, LEVEL + 1) - INSTR (aa, ',', 1, LEVEL)
- 1
) sub
FROM (SELECT ',' || '123,11,4567,8,99999,000,123456' || ',' aa
FROM DUAL)
CONNECT BY LEVEL <= LENGTH (aa) - LENGTH (REPLACE (aa, ',')) - 1
예제 2)
구분기호가 2byte 이상인 일반적인 경우엔 다음과 같이 해준다.
(아래에서 구분기호는 #&)
SELECT SUBSTR (str,
INSTR (str, base, 1, LEVEL) + len,
INSTR (str, base, 1, LEVEL + 1)
- INSTR (str, base, 1, LEVEL)
- len
) sub
FROM (SELECT '#&' base, '#&' || '1#&(#&#&Ɔ' || '#&' str,
LENGTH ('#&') len
FROM DUAL)
CONNECT BY LEVEL <= (LENGTH (str) - LENGTH (REPLACE (str, base))) / len - 1
예제 3)
좀 더 응용해 보자.
이번에는 다음과 같이 여러행이 존재할 때,
COL1
--------------------------------------------------
1/2/3
44/555
3/77
8/77/8
/ 를 기준으로 행으로 분리하면, 즉 아래와 같이 나오려면
1
2
3
44
555
3
77
8
77
8
아래와 같이 한다.
SELECT sub
FROM (SELECT DISTINCT rn, LEVEL,
SUBSTR (str,
INSTR (str, base, 1, LEVEL) + len,
INSTR (str, base, 1, LEVEL + 1)
- INSTR (str, base, 1, LEVEL)
- len
) sub
FROM (SELECT ROWNUM rn, '/' base, '/' || col1 || '/' str,
LENGTH ('/') len
FROM tab2)
CONNECT BY LEVEL <=
(LENGTH (str) - LENGTH (REPLACE (str, base)))
/ len
- 1)
같은 문제인데, distinct 를 사용하지 않고 만들어 봤습니다.
WITH table1 AS
(SELECT 1 c1, 'd2#d3#d4#d4#d6' c2
FROM DUAL
UNION ALL
SELECT 2, 'a2#s3#s4#f4#h6#g4#j6#u8'
FROM DUAL)
SELECT c1,
SUBSTR (str,
INSTR (str, base, 1, level#) + len,
INSTR (str, base, 1, level# + 1)
- INSTR (str, base, 1, level#)
- len
) c2
FROM (SELECT c1, '#' base, '#' || c2 || '#' str, LENGTH ('#') len, level#
FROM table1 a,
(SELECT LEVEL level#
FROM (SELECT MAX (( LENGTH (c2)
- LENGTH (REPLACE (c2, '#'))
+ 1
)
) max#
FROM table1) t
CONNECT BY LEVEL <= t.max#) b
WHERE (LENGTH (a.c2) - LENGTH (REPLACE (a.c2, '#')) + 1) >=
b.level#)
ORDER BY c1, level#
C1 C2
-------
1 d2
1 d3
1 d4 -- 중복 허용
1 d4 -- 중복 허용
1 d6
2 a2
2 s3
2 s4
2 f4
2 h6
2 g4
2 j6
2 u8
글쓴이 : 김홍선
예제 1)
다음과 같은 문자열이 있다.
123,11,4567,8,99999,000,123456
이 문자열을 콤마(,)를 기준으로 행으로 분리해 보자. 즉 아래와 같은 결과가 나오도록 해보자.
123
11
4567
...
...
쿼리는 다음과 같다.
SELECT SUBSTR (aa,
INSTR (aa, ',', 1, LEVEL) + 1,
INSTR (aa, ',', 1, LEVEL + 1) - INSTR (aa, ',', 1, LEVEL)
- 1
) sub
FROM (SELECT ',' || '123,11,4567,8,99999,000,123456' || ',' aa
FROM DUAL)
CONNECT BY LEVEL <= LENGTH (aa) - LENGTH (REPLACE (aa, ',')) - 1
예제 2)
구분기호가 2byte 이상인 일반적인 경우엔 다음과 같이 해준다.
(아래에서 구분기호는 #&)
SELECT SUBSTR (str,
INSTR (str, base, 1, LEVEL) + len,
INSTR (str, base, 1, LEVEL + 1)
- INSTR (str, base, 1, LEVEL)
- len
) sub
FROM (SELECT '#&' base, '#&' || '1#&(#&#&Ɔ' || '#&' str,
LENGTH ('#&') len
FROM DUAL)
CONNECT BY LEVEL <= (LENGTH (str) - LENGTH (REPLACE (str, base))) / len - 1
예제 3)
좀 더 응용해 보자.
이번에는 다음과 같이 여러행이 존재할 때,
COL1
--------------------------------------------------
1/2/3
44/555
3/77
8/77/8
/ 를 기준으로 행으로 분리하면, 즉 아래와 같이 나오려면
1
2
3
44
555
3
77
8
77
8
아래와 같이 한다.
SELECT sub
FROM (SELECT DISTINCT rn, LEVEL,
SUBSTR (str,
INSTR (str, base, 1, LEVEL) + len,
INSTR (str, base, 1, LEVEL + 1)
- INSTR (str, base, 1, LEVEL)
- len
) sub
FROM (SELECT ROWNUM rn, '/' base, '/' || col1 || '/' str,
LENGTH ('/') len
FROM tab2)
CONNECT BY LEVEL <=
(LENGTH (str) - LENGTH (REPLACE (str, base)))
/ len
- 1)
같은 문제인데, distinct 를 사용하지 않고 만들어 봤습니다.
WITH table1 AS
(SELECT 1 c1, 'd2#d3#d4#d4#d6' c2
FROM DUAL
UNION ALL
SELECT 2, 'a2#s3#s4#f4#h6#g4#j6#u8'
FROM DUAL)
SELECT c1,
SUBSTR (str,
INSTR (str, base, 1, level#) + len,
INSTR (str, base, 1, level# + 1)
- INSTR (str, base, 1, level#)
- len
) c2
FROM (SELECT c1, '#' base, '#' || c2 || '#' str, LENGTH ('#') len, level#
FROM table1 a,
(SELECT LEVEL level#
FROM (SELECT MAX (( LENGTH (c2)
- LENGTH (REPLACE (c2, '#'))
+ 1
)
) max#
FROM table1) t
CONNECT BY LEVEL <= t.max#) b
WHERE (LENGTH (a.c2) - LENGTH (REPLACE (a.c2, '#')) + 1) >=
b.level#)
ORDER BY c1, level#
C1 C2
-------
1 d2
1 d3
1 d4 -- 중복 허용
1 d4 -- 중복 허용
1 d6
2 a2
2 s3
2 s4
2 f4
2 h6
2 g4
2 j6
2 u8
댓글 0
번호 | 제목 | 글쓴이 | 날짜 | 조회 수 |
---|---|---|---|---|
94 | 테이블 열항목을 행항목으로 변경하는 팁 | 구퍼 | 2011.01.11 | 8835 |
93 | 오라클 DB 링크 만들기 | 구퍼 | 2011.01.06 | 6826 |
92 | select -> update 구문 샘플 | 구퍼 | 2010.01.21 | 5936 |
91 | Instant Client 사용법 | 구퍼 | 2009.12.30 | 6051 |
90 | Conditions | 구퍼 | 2008.09.17 | 5844 |
89 | Basic Delete Statements | 구퍼 | 2008.09.17 | 4671 |
88 | Basic Update Statements | 구퍼 | 2008.09.17 | 4622 |
87 | Unix, Oracle, Pro*C작성 입찰공고 | 운영자 | 2003.06.05 | 4458 |
86 | Unix, Oracle, Pro*C작성 구인구직게시판 | 운영자 | 2003.06.05 | 4887 |
85 | Unix, Oracle, Pro*C작성 자유게시판 | 운영자 | 2003.06.05 | 4745 |
84 | 최단거리찾기 혹은 멀리 떨어진 두지점간의 거리의 합구하기 | 박상현 | 2006.11.07 | 3690 |
83 | PL/SQL에서 쿼리시 Array Processing 처리방법 | 박상현 | 2006.10.27 | 3622 |
82 | 시간선분(선분이력)의 합집합 구하기 | 박상현 | 2006.06.13 | 5159 |
81 | 최대공약수, 최소공배수 구하기 | 박상현 | 2006.06.13 | 3839 |
80 | 문자열에서 특정 단어 갯수 구하기 | 박상현 | 2006.06.13 | 3573 |
79 | 소수(prime number) 구하기 | 박상현 | 2006.06.13 | 3425 |
78 | 달력 생성 쿼리 | 박상현 | 2006.06.13 | 3345 |
77 | 다중 Row 결과를 단일행으로 컴마로 분리해 출력하는 방법 (2) | 박상현 | 2006.06.13 | 3968 |
76 | 다중 Row 결과를 단일행으로 컴마로 분리해 출력하는 방법 (1) | 박상현 | 2006.06.13 | 3697 |
» | 문자열 행으로 분리하기 | 박상현 | 2006.06.13 | 3827 |