DB - Index

이동훈·2023년 6월 8일
2

SSAFY 프로젝트 발표회를 보면서, 기억에 남은 것 중 하나가 인덱스였다.
자율프로젝트 쯤 되니, 인덱스를 사용하여 쿼리 조회 시간을 단축시켰다는 내용이 심심치 않게 소개되었던 탓이다.


인덱스란?

인덱스는 데이터베이스에서 '데이터 검색 성능 향상 효과'를 얻고자 할 때 사용되는 자료구조이다.

어떻게?
말 그대로 index를 부여해서!

primary key, 혹은 unique not null 제약조건을 가지고 있는 속성을, int(혹은 varchar)와 한데 묶어 인덱스를 생성시켜 놓는 것이다.

그리 함으로서, 이제 우리는 Select 요청이 들어왔을 때, B-Tree로 구성된 logN * Depth 시간복잡도만 소요하여 데이터를 읽어들일 수 있게 되었다.

primary key 속성을 사용 시: 클러스터 인덱스
unique not null 속성을 사용 시 : 세컨더리 인덱스


인덱스의 이점:

Select(조회)가 빨라진다! - 자료가 많은 경우

검색 성능 향상: 인덱스는 데이터의 검색 속도를 빠르게 한다. 인덱스를 통해 검색하려는 데이터의 위치를 더 빠르게 찾을 수 있기 때문.

정렬된 데이터 접근: 인덱스는 주로 B-tree(이진 트리랑 다르다!) 구조를 사용하기 때문에, 데이터를 정렬된 상태로 저장하고 접근한다. 이를 통해 ORDER BY나 GROUP BY와 같은 쿼리를 빠르게 수행할 수 있다.


인덱스의 단점:

장점만 있는 것은 아니다.

저장 공간: 인덱스 자체가 데이터를 복사하여 저장하므로 추가적인 저장 공간을 필요로 한다.

데이터 수정의 오버헤드: 데이터의 추가, 삭제, 수정이 발생하면 인덱스도 함께 갱신되어야 한다. 이러한 특성 때문에, 인덱스의 생성 여부를 정할 때에는 수정이 잦은 테이블보다, 읽기가 주로 이루어질 테이블에 생성하는 것이 좋다.


인덱스의 작동 방식:

대부분의 데이터베이스에서, 인덱스를 구현하기 위한 자료구조로 B-tree 자료구조를 선택하여 사용한다.
B-tree는 이진 탐색 트리를 확장한 것으로, 노드당 여러 키를 가질 수 있고 여러 자식을 가질 수 있는 이진 트리이다.

루트(root) - . . . 브랜치(branch) . . . - 리프(leaf)

B-tree의 생성: 인덱스 생성 시, 트리의 각 노드에는 키와 키에 해당하는 데이터의 위치가 저장된다.

검색: 키 값을 사용해 B-tree를 탐색한다. 이진 탐색 트리와 마찬가지로, 키가 현재 노드의 키보다 작으면 왼쪽 자식을, 크면 오른쪽 자식을 방문한다.

삽입: 새 데이터를 삽입할 때는 해당 키를 B-tree에 추가한다. 이 과정에서 트리의 밸런스를 유지하기 위해 Depth가 깊어질 수 있다.

삭제: 데이터를 삭제할 때는 해당 키를 B-tree에서 제거합니다. 이 과정에서 트리의 밸런스를 유지하기 위해 Depth가 얕아질 수 있다.

갱신: 데이터를 갱신할 때는 해당 키를 B-tree에서 제거하고 새 키를 삽입하여 처리한다.


결론

인덱스에 사용된 B-tree 자료구조는 검색, 삽입, 삭제 연산 모두 O(log n)의 시간 복잡도를 가져, 대량의 데이터에서도 빠른 성능을 보장한다.
하지만! 삽입, 삭제의 경우 Depth 재정렬이 일어날 수 있으므로 오버헤드에 주의해야 한다.

또한 공간적(별도의 공간 필요), 시간적(별도의 인덱스 서칭 시간) 자원의 소모되므로, 인덱스가 필요한 테이블인지 고민한 뒤 선택함이 옳을것이다.

profile
Fool Snack Developer

2개의 댓글

comment-user-thumbnail
2023년 6월 8일

DB 설계 시 데이터량에 따라 인덱스 사용 여부를 고려해보아야겠네요

답글 달기
comment-user-thumbnail
2023년 6월 8일

평소 궁금했던 인덱스의 동작 방식을 잘 이해할 수 있어서 좋았습니다 !!

답글 달기