1. 개요

- 어떤 기능을 갖고 어떤 엔티티를 어떤 방식으로 저장하는 데이터베이스를 구축할 것인지(개념적 데이터베이스)부터 schema를 어떻게 정의해 데이터베이스를 구축할 것인지(논리적 데이터베이스), 물리적 장치를 어떠한 방식으로 제어해 데이터베이스를 구축할 것인지(물리적 데이터베이스)를 결정하는 것을 통틀어 데이터베이스 설계라 한다.

- 개념적 데이터베이스를 설계할 때 ER 모델 또는 정규화 모델을 사용하여 이를 판단할 수 있으며, 이를 실제로 논리적으로 구현한 데이터 모델로는 RDB 모델, 계층형 DB 모델, 네트워크형 DB 모델 등이 있다.

- 엔티티(entity)는 서로 구분되는 개별적 단위(사람, 사물, 장소 등)로서 DB를 사용하려는 주체가 DB에서 표현하고자 하는 객체 하나하나를 일컬으며, 관계(relationship)는 서로 다른 둘 이상의 엔티티 사이에 있는 논리적 상관관계를 의미한다. 개념적 데이터베이스를 설계할 때 구체적으로 DB에 표현하고자 하는 내용을 엔티티와 엔티티 사이 관계를 규정해나가는 방식으로 설계하게 된다.

2. 데이터베이스 설계 과정

- 보통 다음 과정을 거쳐 DB를 구축하게 된다.

(1) DB를 사용하려는 주체의 요구사항을 분석한다.

(2) 개념적 설계

  • 요구사항을 충족하기 위해 어떤 엔티티를 DB에 표현해야 하는지, 각 엔티티 사이에는 어떤 관계가 있는지 등을 분석한다. 이 과정에서 구체적 DBMS에 맞는 스키마를 작성하기 전에 개념적 스키마를 작성한다. (ER 모델로 개념적 스키마를 작성하는 경우 이때의 개념적 스키마를 ER 다이어그램으로 표현한다.)

  • 이 단계에서 각 엔티티가 갖는 속성을 분석하고 각 속성값의 도메인, 후보키/기본키, 엔티티/관계의 타입 등을 결정한다.

  • 개념적 설계 단계를 생략하는 경우도 있으나, 이 경우 논리적 설계 시 여러 현실적, 기술적 문제에 부딪혀 오히려 더 생산성이 낮아질 수 있다.

(3) 논리적 설계

  • DBMS를 선택하고, 개념적으로 설계한 내용을 토대로 논리적 스키마를 작성한다. 작성된 논리적 스키마를 정규화하여 성능을 개선할 수 있게 한다.

  • 논리적 스키마는 DBMS 내 알고리즘을 통해 ER 다이어그램으로 작성된 개념적 스키마로부터 그대로 매핑될 수 있다.

  • DBMS를 선택할 때에는 정치적, 경제적 요인 등 여러 현실적 요인이 고려될 수 있다.

(4) 물리적 설계

  • 작성된 스키마를 토대로 성능을 고려하여 실제 물리적 DB를 설계한다. 물리적 설계 시에는 어떤 엔티티에 관한 어떤 종류의 트랜잭션이 어느 정도 빈도로 일어나는지, 각 유형의 쿼리에 대한 응답시간은 얼마나 걸릴지 등을 고려하여 물리적 설계를 하게 된다. (예를 들면, ‘더 높은 빈도로 발생하는 트랜잭션의 처리에 관해 더 높은 우선순위를 부여한다’ 같은 사항이 이 단계에서 결정된다.)

(5) 보안 설계

(6) 구현

3. ER 모델, 엔티티, 애트리뷰트, 관계

- 요구사항을 분석한 후 가장 먼저 개념적 데이터베이스를 설계한다. ER 모델은 1976년 P. P. Chen이 제안한 개념적 데이터베이스 설계 모델로, 현재 가장 널리 쓰이는 개념적 데이터베이스 설계 모델이다. ER 모델은 DB에 표현하고자 하는 것들을 엔티티, 엔티티의 애트리뷰트, 엔티티 사이 관계로 표현한다. 배우고 이해하기 쉽고 표현력이 뛰어나며, 여러 DBMS에서 지원하는 RDB 모델로 매핑하기도 쉬운 등 여러 강력한 장점들이 있어 개념적 데이터베이스를 설계할 때 대부분 이 모델을 사용해 설계를 한다.

- 엔티티(entity)는 서로 구분되는 개별적 단위(사람, 사물, 장소 등)로서 DB를 사용하려는 주체가 DB에서 표현하고자 하는 객체 하나하나를 말한다.

- 애트리뷰트(attribute)는 그 엔티티가 갖는 고유한 특징을 설명하는 개념으로, 엔티티끼리는 각각 다른 애트리뷰트를 가질 수 있고 한 엔티티는 여러 애트리뷰트를 가질 수 있다. (예를 들어, 사람이라는 엔티티는 각자 이름, 사는 곳, 키, 몸무게 같은 고유한 애트리뷰트를 가진다.) 엔티티와 달리 그 자체로는 독립된 의미를 갖지 않는다. ER 다이어그램에서 타원으로 표현하며, crow’s foot 표기법에서는 엔티티 타입을 표현한 직사각형 안의 목록으로 표기된다.

  • 엔티티 타입: 엔티티가 가질 수 있는 애트리뷰트 틀을 말하며, 이 틀 안에 하나 이상의 엔티티가 속할 수 있다. RDB 모델에서 릴레이션의 스키마가 ER 모델의 엔티티 타입에 대응된다. ER 다이어그램과 crow’s foot 표기법 모두 직사각형으로 표현하며, ER 다이어그램에서는 그 엔티티 타입에 속하는 애트리뷰트를 표현한 타원과 실선으로 이어진다.

  • 엔티티 집합: 속성이 같은 엔티티들끼리 각각 그룹을 지어 구분해둘 수 있으며, 이때 속성을 기준으로 그룹 지어진 엔티티들을 ‘엔티티 집합’이라 한다. RDB 모델에서 특정 시점에서 어느 한 릴레이션에 속한 모든 튜플집합이 ER 모델의 엔티티 집합에 대응된다.

  • 키 애트리뷰트: 같은 엔티티 타입을 갖는 엔티티들이 갖는 애트리뷰트들 중에서, 그 엔티티들을 각각 고유하게 식별하게 하는 애트리뷰트. ER 다이어그램과 crow’s foot 표기법 모두 그 이름에 밑줄을 긋는 것으로 표현한다.

  • 강한 엔티티 타입, 약한 엔티티 타입, 식별 엔티티 타입, 부분키: 키 애트리뷰트를 갖는 엔티티 타입을 강한 엔티티 타입, 갖지 않는 엔티티 타입을 약한 엔티티 타입이라 한다. 약한 엔티티 타입은 관계 타입을 통해 다른 엔티티 타입과 결합했을 때 자신의 애트리뷰트 중 자신의 엔티티들을 각각 고유하게 식별하는 애트리뷰트를 갖는 경우가 있다. 이때 그 애트리뷰트를 부분키(partial key)라 하고, 부분키를 갖게 하는 다른 엔티티 타입을 소유 엔티티 타입 또는 식별 엔티티 타입이라 한다. 부분키는 ER 다이어그램에서 그 이름에 점선으로 밑줄을 긋는 것으로 표현하며, 약한 엔티티 타입은 ER 다이어그램에서 테두리가 이중선인 직사각형으로 표현한다.

  • 단순 애트리뷰트: 다른 애트리뷰트로 나뉘지 않는 애트리뷰트.

  • 복합 애트리뷰트: 둘 이상 애트리뷰트를 갖는 애트리뷰트. 예를 들어, ‘주소지’라는 애트리뷰트는 국가, 도시, 번지수, 동호수 같은 애트리뷰트를 갖는다. ER 다이어그램에서 자신이 갖는 다른 애트리뷰트들과 실선으로 이어진다.

  • 단일값 애트리뷰트: 그 엔티티가 오로지 하나의 값만을 갖는 애트리뷰트. 예를 들어 ‘사람’이라는 엔티티의 ‘탄생 년도’라는 애트리뷰트는 둘 이상 값을 가질 수 없으므로 단일값 애트리뷰트다.

  • 다중값 애트리뷰트: 엔티티에 따라 둘 이상의 값을 가질 수도 있는 애트리뷰트. 예를 들어 ‘사람’이라는 엔티티의 ‘친구’라는 애트리뷰트는 둘 이상의 값을 가질 수 있으므로 다중값 애트리뷰트다. ER 다이어그램에서 테두리가 이중선인 타원으로 표현한다.

    • 애트리뷰트가 가질 수 있는 값이 여러 개이고 그에 따르는 조건이 각각 다른 경우 ER 스키마 작성 시 이를 엔티티 타입과 그에 따르는 애트리뷰트로 변경하는 게 바람직할 수 있다.
  • 저장된 애트리뷰트와 유도된 애트리뷰트: 애트리뷰트 중에는 그 자체로 독립적인 값을 갖는 애트리뷰트(저장된)가 있고 다른 애트리뷰트 값을 통해 얻어지는 애트리뷰트(유도된)가 있다. 예를 들어 ‘사람’이라는 엔티티의 ‘탄생일’이라는 애트리뷰트는 그 자체로 독립적인 값을 갖지만, ‘나이’라는 애트리뷰트는 그 사람 엔티티의 탄생일 애트리뷰트를 통해 얻는 애트리뷰트다. 전자를 저장된 애트리뷰트, 후자를 유도된 애트리뷰트라 한다. 유도된 애트리뷰트는 RDB 모델을 구현할 때에는 릴레이션의 스키마에 포함하지 않는 게 좋다. 유도된 애트리뷰트는 ER 다이어그램에서 테두리가 점선인 타원으로 표현한다.

- 관계(relationship)는 서로 다른 엔티티 사이에 존재하는 상관관계를 설명하는 개념이다. 예를 들어 ‘A라는 사람은 B라는 장소에 살고 있다’ 할 때 여기서 A와 B가 엔티티라면 “살고 있다”는 A, B 사이의 상관관계를 설명하는 개념으로서 여기서 말하는 ‘관계’에 해당한다.

  • 관계 타입과 관계 집합: 동질의 관계를 묶는 틀을 관계 타입, 이처럼 동질의 관계들을 한데 묶어 관계 집합이라 한다. 관계 타입은 엔티티 타입과 마찬가지로 그것이 갖는 고유한 특징을 설명하는 애트리뷰트를 가질 수 있다. 예를 들어, ‘(사람들이 A라는 장소에) 살고 있다’라는 관계 타입은 ‘A에 살고 있는 사람 수’라는 애트리뷰트를 가진다. 관계 타입은 서로 다른 엔티티 타입 사이에 둘 이상일 수 있다. ER 다이어그램에서 마름모로 표현하며, 그 관계 타입이 설명하는 엔티티 타입, 그 관계 타입에 속하는 애트리뷰트와 실선으로 이어진다. crow’s foot 표기법에서는 단순히 엔티티 타입과 엔티티 타입 사이를 실선으로 긋고 그 위에 그 관계 타입의 이름을 적는 것으로 표현한다.

  • 차수(degree): 어떤 관계 타입에 연결돼 있는 엔티티 타입의 수를 그 관계 타입의 차수라 한다. 대부분 관계 타입의 차수는 2이지만, 그보다 적을 수도 있고 많을 수도 있다.

  • 카디날리티(cardinality): 서로 다른 두 엔티티 타입이 관계 타입을 통해 연결돼 있을 때, 각 엔티티 타입을 구성하는 엔티티들은 다른 엔티티와 일대일로 연결돼 있을 수도 있고, 아무 연결이 없거나 1:N 또는 M:N의 비율로 연결돼 있을 수도 있다. 이때 각 엔티티가 관계에 참여할 수 있는 수를 카디날리티라 한다. 카디날리티 수는 ER 다이어그램에서 엔티티 타입과 관계 타입을 잇는 실선 위에 (카디날리티 최솟값, 카디날리티 최댓값)으로 표현하는데, 최솟값이 0인 경우 괄호 없이 최댓값만 표현하기도 한다. crow’s foot notation에서는 엔티티 타입과 엔티티 타입을 잇는 실선이 각 엔티티 타입에 붙어 있는 연결부분에 특별한 표시를 해서 카디날리티를 표현한다.

- 관계 타입과 엔티티 타입 사이 관계를 보다 명확히 하기 위하여 역할(role)이라는 개념을 사용하기도 한다. 예를 들어 ‘직원’이라는 엔티티 타입이 ‘상하관계’라는 관계 타입과 차수 1로 이어져 있을 때, 어떤 엔티티는 다른 직원 엔티티에 대해 상급자일 수 있고 또 다른 직원 엔티티에 대해서는 하급자일 수 있다. 이런 경우에는 그 엔티티 타입의 엔티티가 다른 엔티티들에 대해 각각 역할이 다른 연결 관계를 가지기 때문에 그 엔티티 타입과 관계 타입 사이에 역할이 다른 연결이 두 가지 있음을 명시해야 한다. ER 다이어그램에서 엔티티 타입과 관계 타입 사이에는 두 개의 실선을 긋고 각 실선마다 그에 대응되는 역할을 표시한다.

- 서로 다른 두 엔티티 타입이 어떤 관계 타입으로 연결돼 있을 때, 한쪽 엔티티 타입의 모든 엔티티가 다른 엔티티 타입에 연결된 경우를 전체 참여라 하고, 일부 엔티티는 연결되지 않은 경우를 부분 참여라 한다. 전체참여는 ER 다이어그램에서 이중 실선으로 표현한다.

  • 약한 엔티티 타입은 항상 다른 엔티티 타입과 전체 참여한다. 이러한 관계 제약조건은 DB 구축에 있어 매우 중요한 제약조건 중 하나다.

4. 논리적 스키마 작성

- DB 설계 과정에서 개념적 스키마를 토대로 논리적 스키마를 작성하는 과정이 필요하다. 단순히 생각하면 모든 간선마다 릴레이션을 생성해도 되지만(이렇게 되면 각 간선마다 속성이 2개인 릴레이션이 생성되며 이를 binary relation이라 한다) 이렇게 되면 데이터가 필요할 때마다 수도 없이 많은 횟수의 join 연산을 수행해야 하며 이는 대단히 비효율적이다.

- 이보다 더 효과적인 성능을 보일 수 있게 ER 스키마를 DBMS의 릴레이션으로 매핑하는 알고리즘이 있다. 이 알고리즘은 ER 스키마 내 각 요소의 특성을 반영하여 단계적으로 ER 스키마를 릴레이션으로 매핑한다.

1) 단일값 애트리뷰트만을 갖는 모든 엔티티 타입을 릴레이션으로 매핑하기

- ER 스키마 내 단일값 애트리뷰트만을 갖는 모든 강한/약한 엔티티 타입에 대응되는 릴레이션을 각각 생성한 후, 그 엔티티 타입이 갖는 애트리뷰트들을 각각 그 릴레이션의 애트리뷰트로서 릴레이션에 포함시킨다.

  • 기존 엔티티 타입의 복합 애트리뷰트는 그 릴레이션에 포함시키지 않고 그 하위 단순 애트리뷰트들만을 그 릴레이션의 애트리뷰트로서 포함시킨다.

  • 약한 엔티티 타입의 경우 그 엔티티 타입에 연결된 소유 엔티티 타입의 기본키를 그 엔티티 타입의 릴레이션에 (소유 엔티티 타입의 기본키를 참조하는 외래키로서) 포함시킨다.

- 어떤 애트리뷰트가 기본키가 되는지는 강한 엔티티 타입과 약한 엔티티 타입에 차이가 있다.

  • 강한 엔티티 타입: 각 엔티티 타입의 키 애트리뷰트가 그에 대응되는 릴레이션의 기본키가 된다.

  • 약한 엔티티 타입: 약한 엔티티 타입에 대응되는 릴레이션의 기본키는 원래 그 릴레이션에 포함되는 부분키와 외래키의 조합으로 이루어진다.

2) 차수가 2인 관계 타입을 릴레이션으로 매핑하기

(1) 그 관계 타입에 대응되는 릴레이션을 생성한 후, 그 관계 타입과 연결된 각 엔티티 타입에 대응되는 릴레이션의 기본키를 그 관계 타입의 릴레이션에 (각 릴레이션의 기본키를 참조하는 외래키로서) 포함시킨다. 이때 외래키의 조합이 그 릴레이션의 기본키가 된다. (1:1, 1:N, M:N 관계 타입의 경우)

  • 장점: 상세한 documentation의 설명 없이도 관계의 의미를 명확히 파악할 수 있는 DB를 구축할 수 있다.

  • 단점: 관계의 의미를 반영한 데이터를 추출할 때마다 join 연산을 두 번씩 수행해야 하는데 이는 상당한 overhead를 발생시킬 수 있다.

(2) 그 관계 타입에 연결된 엔티티 타입들에 대응되는 두 릴레이션에 대해, 한 릴레이션의 기본키를 다른쪽 릴레이션에 외래키로서 포함시킨다. (1:N 관계 타입이라면, 1쪽 릴레이션의 기본키를 N쪽 릴레이션에 외래키로서 포함시킨다.) 관계 타입의 애트리뷰트들은 외래키를 갖는 릴레이션에 포함시킨다. (1:1, 1:N 관계 타입의 경우)

  • 장점: 외래키를 통해 두 릴레이션 사이에 어느 정도 관계가 있음을 유추할 수 있으며, join 연산의 횟수도 적절히 사용해 비교적 적은 overhead가 발생한다.

  • 단점: 릴레이션을 따로 두는 것보다는 관계의 의미를 비교적 명확히 파악하기 어려우며, 어떤 릴레이션의 기본키를 외래키로 하는지에 따라 overhead가 크게 발생할 위험이 있다.

(3) 두 엔티티 타입에 대응되는 릴레이션의 튜플들을 모두 연결시킨 튜플들로 새 릴레이션을 만든다. (1:1 관계 타입의 경우)

  • 장점: 데이터 추출 시 join을 아예 하지 않으므로 성능이 뛰어나다.

  • 단점: documentation의 상세한 설명이 없다면 독립된 엔티티과 관계가 있었다는 사실을 알기 매우 어려워진다.

3) 차수가 3 이상인 관계 타입을 릴레이션으로 매핑하기

- 그 관계 타입에 대응되는 릴레이션을 생성한 후, 그 관계 타입과 연결된 각 엔티티 타입에 대응되는 릴레이션의 기본키를 그 관계 타입의 릴레이션에 (각 릴레이션의 기본키를 참조하는 외래키로서) 포함시킨다. 이때 외래키의 조합이 그 릴레이션의 기본키가 된다.

4) 다중값 애트리뷰트를 릴레이션으로 매핑하기

- 그 다중값 애트리뷰트에 대응되는 릴레이션을 생성한 후, 그 다중값 애트리뷰트를 갖는 엔티티 타입 또는 관계 타입에 대응되는 릴레이션의 기본키를 그 다중값 애트리뷰트의 릴레이션에 (각 릴레이션의 기본키를 참조하는 외래키로서) 포함시킨다. 이때 외래키의 조합이 그 릴레이션의 기본키가 된다.