1. DB 반정규화란?
- 성능 향상을 위해 정규화를 포기하는 것.
- 즉, 성능 향상을 위해서 데이터 중복을 허용하고 조인을 줄이는 용도로 사용한다.
- 당연한 이야기지만, 모델 간 종속성이 높아지고 확장성이 떨어지지만, 조회 속도를 향상시킬 수 있다.
1) 반정규화 문제점
- 데이터의 무결성이 항상 보장되지는 않으므로 제한적으로 사용해야한다.
2. 테이블 반정규화
- 테이블 병합, 분할, 추가로 반정규화를 진행한다.
1) 테이블 병합
- join을 수행하지 않도록 테이블을 통합하여 성능을 높이는 것을 의미
2) 테이블 분할
(1) vertical partitioning
- 컬럼 단위로 테이블을 1:1 분리
[1] 수직 분할 예시
id | name | phone |
1 | dexter | 01022223333 |
2 | bob | 01033334444 |
- vertical partitioning 적용
id | name |
1 | dexter |
2 | bob |
id | phone |
1 | 01022223333 |
2 | 01033334444 |
[2] vertical partitioning 장점
- 특정 칼럼들만 CRUD 작업하고 싶을 때, 필요한 부분만 작업할 수 있어서 성능이 향상된다.
[3] vertical partitioning 단점
- 테이블들에 있는 데이터가 모두 필요한 경우 테이블 간 join 비용이 증가한다.
(2) sharding
- row 단위로 테이블을 분리
[1] sharding하는 이유
- 하나의 테이블이 너무 많은 데이터를 가지고 있으면 용량 이슈가 생길 수 있다.
- CRUD 작업이 서비스 성능에 영향을 줄 수 있다.
- 그래서 DB 트래픽을 분산하기 위해 사용한다.
[2] 어떤 규칙으로 테이블을 자를지 방법
- Shard key를 어떻게 정의하느냐에 따라 데이터를 효율적으로 분산시키는 것이 결정된다.
첫 번째, Hash sharding
- 특정 조건에 따라 key값을 정의하는 것을 의미.
- 한 예로,
key 조건 : id % 4
cluster [node0, node1, node2, node3]
- 이렇게 정의하면 id의 나머지에 따라 각각의 노드에 분산되어 저장된다.
- 단점은 규칙을 바꾸어야 하기 때문에 모든 노드에 데이터가 차면 확장하는데 어려움이 있다.
ps.
- cluster란 0,1,2,3 노드들의 집합을 의미
- 각 node는 table을 의미.
두 번째, Dynamic sharding
- 특정 순서에 따라 key값을 정의하는 것을 의미.
- 보통 한 테이블에서 id 번호 순서에 따라 각 노드에 데이터를 배정한다.
- 한 예로,
- 0~30, 31~60, 61~90,,,, 이렇게 배정하는 방식이다.
- 장점은 나중에 노드를 추가하는데 용이하다.
3) 테이블 추가
(1) 중복테이블 추가
- 타 서버에 있는 테이블과 동일한 구조의 테이블을 본 서버에 추가
- 그래서 원격 조인방지
(2) 통계테이블 추가
- 통계값을 미리 계산해서 저장하는 테이블 추가
order
id | account_id | order_date | product_id |
... |
order_statistic
id | order_date | 일일주문수량 | 일일주문금액 |
... |
(3) 이력테이블 추가
- 마스터 테이블에 존재하는 row를 트랜잭션 발생 시점에 따라 복사해두는 테이블 추가
(4) 부분테이블 추가
- 자주 조회되는 컬럼들만 별도로 모아놓은 테이블 추가
3. 컬럼 반정규화
- 중복, 파생, 이력테이블 컬럼 추가로 표현한다.
1) 중복컬럼 추가
- join 프로세스를 줄이기 위해 중복 컬럼 추가
- SELECT 비용은 감소하지만 UPDATAE 비용은 증가
account
id | name |
order
id | account_id |
order_product
id | order_id |
delivery
id | order_id | order_product_id | account_id |
- 배달 테이블이 원래는 회원 id와 연관관계가 존재하지 않는다. order 테이블을 거쳐서 delivery 테이블에 도달해야하므로 join 비용이 증가한다. 검색 효율을 향상시키기 위해 account_id를 delivery 테이블에 추가한다.
2) 파생컬럼 추가
- 계산을 통해 얻어지는 결과값을 테이블에 컬럼으로 저장
order
id | account_id | total_price(파생컬럼) |
order_product
id | order_id | order_count |
product
id | order_product | price |
- product 테이블의 price와 order_product 테이블의 order_count를 곱해서 total_price로 order 테이블에 저장
3) 이력테이블 컬럼 추가
- 이력 테이블에 기능성 컬럼 추가(최신 여부, 시작일 or 종료일 등)
product
id | price |
product_price_log(이력테이블)
id | product_id | update_date | old_price | recent_price |
4. 관계 반정규화
- 중복관계 추가
1) 중복관계 추가
- 데이터 처리를 위해 여러 경로를 거쳐야 할 경우 관계를 중복시킴으로써 성능 개선
- 한 예로, "회원 - 주문 - 주문상품 - 배송", 이러한 관계가 있다고 가정할 시, 회원 - 배송까지 가려면 4개의 테이블을 조인해야한다. 그래서 배송에 회원 id 연관관계를 넣어서 join 비용을 줄인다.
- 자세한 예는 중복컬럼 추가를 참고하길 바란다.
reference
https://www.youtube.com/watch?v=SS6H2whbfwc
'Database > MySQL' 카테고리의 다른 글
Host 'host_name' is blocked because of many connection errors.Unblock with 'mysqladmin flush-hosts' (0) | 2022.11.17 |
---|---|
데이터베이스 정규화(Normalization) (0) | 2022.05.23 |
트랜잭션 특징 (0) | 2022.05.07 |
PK, FK 특징 (0) | 2022.05.07 |
mysql settings (0) | 2022.01.30 |