심심한데, SQL 이야기를 꾸려볼까 합니다.
그 첫번째로 UNION 이야기를 할까합니다.
오늘 회사에서 있었던 일로,
우정국에서 우편번호를 2003년 1월 1일자로 또 바꾸었더군요.
결국 기존 데이터를 업데이트하면서 이번에는 우편번호를 RDBMS에 집어넣고 꺼내쓰려고 계획했습니다. (예전에는 dbm hash로 설계했었지요. RDBMS와 비교도 안될 정도의 속도는 나오지만, 우리나라처럼 우편번호가 이렇게 시시때때로 바뀌게 될 경우라면 유지보수가 까다롭네요.)
아무튼 우정국에서 제시한 우편번호의 자료구조는 다음과 같습니다.
Table "newzipcode"
Column | Type | Modifiers | Description
---------+--------+----------+-------------
zipcode | text | | 우편번호
sido | text | | 시/도
gugun | text | | 구/군
dong | text | | 동
ri | text | | 리/대표건물
bunji | text | | 번지
seq | integer | | 일련번호
Indexes: newzipcode_dong_i,
newzipcode_ri_i,
newzipcode_zipcode_i
Unique keys: newzipcode_seq_i
여기서 '동'이나, '리/대표건물명'으로 검색을 한다고 했을때,
단순하게 생각한 쿼리라면,
SELECT * FROM newzipcode
WHERE dong LIKE '종로3가%' OR ri LIKE '종로3가%'
이런식이으로 하면 되겠지요.
하지만, 여기서 주의해야할 것은 바로 or 조건입니다.
or 조건은 인덱스를 사용할 수 없습니다. 당연한 처리겠지요.
윗 쿼리의 가장 합리적인 처리는 '동'에서는 newzipcode_dong_i 인덱스를 사용하고,
'리'에서는 newzipcode_ri_i 인덱스를 사용하는 것이겠지요.
그런데, 하나의 쿼리문에서는 두개 이상의 인덱스를 사용할 수도 없으니,
이것에 대한 단순한 생각은 쿼리를 두번 사용한다는 것이겠지요.
바로 이럴 때, 이 두개의 쿼리를 union으로 묶는 것입니다.
SELECT * FROM newzipcode
WHERE dong LIKE '종로3가%'
UNION
SELECT * FROM newzipcode
WHERE ri LIKE '종로3가%'
이렇게 하면, 처음에 꿈꾸었던 그 완벽한(?) 쿼리가 되는 샘이지요.
--
(물론 좀더 꼼꼼하게 생각한다면, union은 '합집합'이라기보다는 두개를 쿼리를 단순하게 합치는 것이기 때문에, 두개의 쿼리안에 같은 자료가 있다면, 중복되어서 나타납니다. 이것에 대한 고려는 이 투토리얼에서 다룰 범위는 아닌 것같습니다)
또 심심하면, SQL 이야기 2를 꾸며보지요.
좋은 날 되소서.
|