ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • [Database] 키(Key)란 무엇인가?
    Database 2022. 8. 21. 21:39

      MySQL과 같은 상용 DBMS(Database Management System)를 이용하여 테이블을 설계하다 보면 가장 먼저 고려해야 하는 사항이 하나 있습니다. 바로 데이터 베이스의 '키(Key)'입니다. 어떤 테이블을 만들려면 해당 테이블의 기본키(Primary Key)가 무엇이 되어야 할지를 반드시 결정해야 합니다. 그렇다면 키란 정확히 무엇일까요? 그 이름에서 미루어 짐작해 보건대, 데이터 베이스를 다룰 때 매우 핵심적인 역할을 수행한다는 것만은 분명해 보입니다.

     이 글에서는 데이터베이스 키에 대해 자세히 알아보고자 합니다. 하지만 키가 무엇인지 알아보기 앞서, 가장 먼저 데이터 베이스에서 키가 정의되고 자신의 역할을 수행하기 위한 맥락인 릴레이션(Relation)의 개념에 대해 살펴보고 키를 알아보겠습니다.

     

    관계 데이터 모델

     가장 먼저 릴레이션(Relation)이 무엇인지에 대해 살펴보겠습니다. 우리가 데이터베이스를 사용하는 이유는 현실 세계에 존재하는 복잡한 데이터 집합을 논리적으로 정의하고 구조화하여 그것을 보다 쉽게 다루길 원하기 때문입니다. 그러기 위해 가장 먼저 해야하는 일은 데이터베이스에 저장하여 다루고자 하는 특정 개체를 모델링하는 것입니다. 현실 세계에 존재하는 데이터를 어떠한 모델링 없이 그대로 데이터베이스에 저장한다면 복잡함이 조금도 줄어들지 않을 것이기에 데이터베이스에 저장하는 일이 무의미할 것입니다.

     현실 세계의 데이터를 모델링하는 방법은 다양하게 존재합니다. 그래프 형태로 여러 개체를 연결하여 관리하는 '네트워크형 데이터 모델'도 존재하고, 계보도처럼 위에서 아래로 뻗어 나가는 형태의 '트리형 데이터 모델'도 존재합니다. 그중에서 대부분의 경우 가장 많이 사용되는 모델은 바로 '관계 데이터 모델'입니다. 즉 여러 개체들이 서로 관계를 맺는 형태로 데이터베이스에서 관리되는 모델이죠. 흔히 RDBMS(Relational Database Management System)라고 하는 Oracle, MySQL, PostgreSQL과 같은 상용 RDBMS들이 이 '관계형 데이터 모델'을 기반으로 설계되었습니다.

     이 관계 데이터 모델에서 데이터를 모델링할 때 사용하는 2차원 테이블을 릴레이션(Relation)이라고 합니다. 어떤 개체를 관계 데이터 모델로 표현하고자 할 때 바로 이 릴레이션이라는 개념을 사용하여 표현하는 것입니다. 릴레이션에는 조금 더 구체적으로 살펴보아야 하는 기본적인 용어와 표현방법들이 존재하는데요. 이것들을 한 번 살펴보겠습니다.

     

     

    릴레이션(Relation)

    학생 릴레이션

     위의 사진은 학생 릴레이션의 한 예를 보여주고 있습니다. 이 예를 통해 릴레이션에서 사용되는 기본적인 용어를 정의해보겠습니다. 먼저 이 2차원 테이블의 가장 첫 번째 행을 각각 차지하고 있는 이름, 학번 학년, 학과, 주소를 이 릴레이션의 속성(Attribute)라고 합니다. 그리고 이렇게 속성들이 모두 모여 이 릴레이션의 스키마(Schema)를 형성합니다. 즉 릴레이션의 틀을 형성하는 것이죠. 맨 위의 행(스키마)을 제외한 나머지 행 각각을 릴레이션의 투플(Tuple)이라고 합니다. 릴레이션을 통해 다루고자하는 학생 한 명 한 명에 대응하는 데이터 집합을 의미합니다. 그리고 학년 속성의 도메인은 1, 2, 3, 4로만 정의됩니다. 보통 대학교의 학년은 1~4학년까지만 정의될 수 있으니까요.

     실세계에 존재하는 학생이라는 개체를 데이터베이스에 저장하기 위해 하나의 릴레이션으로써 단순화하고 구조화하여 표현해보았습니다. 실제로 MySQL에서 이러한 학생 릴레이션을 학생 테이블로 구조화하여 데이터베이스를 형성하고 관리할 수 있습니다.

     그런데 여기서 자연스럽게 드는 의문이 하나 있습니다. 데이터베이스에 학생이라는 개체를 저장하여 관리한다는 것은 단순히 저장만 한다는 것을 의미하는 것이 아닙니다. 언제든지 저장된 내용을 꺼내볼 수도 있고 수정 및 삭제할 수도 있어야 합니다. 그러려면 위의 릴레이션 상에 단 하나의 투플을 구별 지어 특정할 수 있어야 하는데요. 위의 경우에 어느 한 학생을 특정하기 위해 가장 먼저 떠오르는 속성은 아마도 '학번'일 것입니다. 릴레이션 상에 저장된 모든 학생의 학번은 유일할 테니까요. 즉 이 '학번'이라는 속성을 이용한다면 위의 학생 릴레이션에서 그 외의 모든 속성을 비교할 필요 없이 제가 찾고자 하는 어느 특정한 한 학생을 찾아낼 수 있습니다. 이렇게 릴레이션에 저장된 각각의 투플을 구별하는 역할을 하는 속성 또는 속성의 집합을 바로 릴레이션의 키(Key)라고 말합니다. 여기서는 '학번'이라는 속성이 한 가지 키가 될 수 있습니다.

     

     

    유일성과 최소성

     바로 위에서 저는 학번이라는 속성이 '한 가지' 키가 될 수 있음을 이야기했습니다. 또 릴레이션 상에서 투플을 구별하는 역할을 하는 속성 또는 '속성의 집합'을 키로 정의했습니다. 이것은 어느 릴레이션에서 키가 하나 이상 존재할 수 있음을 내포합니다. 즉 키는 속성의 조합에 따라 유일할 수도 있지만 여러가지로 정의될 수도 있습니다.

     당연하게도 릴레이션의 각 속성이 모두 키가 될 수 있는 것은 아닙니다. 어느 속성이 키의 역할을 수행하려면 반드시 특정 조건을 만족해야 합니다. 바로 '유일성'이라는 조건입니다. 즉 릴레이션 상에서 키의 역할을 수행하는 속성값이 중복되어서는 안 됩니다. 위의 학생 릴레이션에서는 학번이라는 속성의 값이 둘 이상 존재해서는 안 됩니다. 이는 상식적으로 생각해보더라도 지극히 당연합니다. 각 투플을 유일하게 구분 지으려면 유일한 값으로 비교해야 할 테니까요.

     일단 이 유일성을 만족하는 속성은 해당 릴레이션에 키가 될 자격을 얻습니다. 여기서 추가적으로 키의 속성에 한 가지가 더 존재하는데요. 바로 '최소성'이 그것입니다. 위의 예를 통해 살펴보자면, 학번이라는 속성은 유일성과 최소성을 모두 만족하는 키입니다. 학번 값은 각 투플에서 유일하므로 유일성을 만족하고 키를 이루는 속성이 학번 하나이므로 최소이기 때문입니다. 반면에 (이름, 학번)을 하나의 속성 조합으로 본다면 이것은 유일성을 만족하므로 일단 키가 될 수 있습니다. 하지만 최소성을 만족하지는 못합니다. 왜냐하면 학번만으로도 충분히 각 투플을 구분 지을 수 있는 키가 될 수 있는데 굳이 이름이라는 속성을 키의 일부분으로 넣었기 때문이죠.

     이처럼 키에는 유일성과 최소성이라는 두 가지 중요한 특성이 존재합니다. 일단 유일성은 릴레이션에서 어느 속성이 키이기 위해 반드시 만족해야 하는 필요충분조건입니다. 그리고 최소성이라는 특성을 만족했는지 여부에 따라 키는 여러 종류로 나뉠 수 있습니다.

     

     

    키의 종류

     키는 크게 슈퍼키(Super Key), 후보키(Candidate Key), 기본키(Primary Key), 대체키(Alternate Key), 외래키(Foreign Key) 다섯 가지로 분류할 수 있습니다. 외래키는 따로 설명하기로 하고 그 외 나머지 키부터 하나하나 살펴보도록 하겠습니다.

     위에서 언급했듯이 어느 속성이 키가 되기 위해서는 유일성을 만족해야 합니다. 그리고 이 유일성을 만족하는 속성 또는 속성들의 집합을 바로 슈퍼키라고 말합니다. 위의 예에서는 학번, (이름, 학번), (학번, 학년) 등등이 슈퍼키가 될 수 있겠네요. 유일성에 추가적으로 해당 속성 집합이 최소성까지 만족하고 있다면 해당 속성 집합을 후보키라고 말합니다. 위의 예에서 보면 학번은 후보키입니다. 유일성과 최소성 둘 다를 만족하기 때문입니다. 또한 (이름, 주소)를 키로 설정한다면 이 속성 집합은 후보키가 될 수 있습니다. 일반적으로 볼 때 이름과 주소가 모두 동일한 투플은 존재하지는 않으니까요. 반면에 (이름, 학번) 속성 조합은 슈퍼키는 될 수 있지만 후보키는 될 수 없습니다. 최소성을 만족하지 않기 때문입니다.

     기본키는 여러 후보키 중에서 해당 릴레이션의 단 하나의 대표키로 사용되기 위해 선정된 키를 의미합니다. 대체키는 기본키로 선택되지 못한 나머지 후보키를 의미하구요. 이렇게 다양한 키의 종류를 유일성과 최소성이라는 특성에 따라 집합 관계로 표현해 보면 다음과 같습니다.

    집합 관계로 표현한 키의 종류

     릴레이션을 설계할 때는 반드시 키를 정해야 합니다. 이때의 키란 기본키를 의미합니다. 즉 유일성과 최소성을 갖춘 여러 속성 집합들 중에서 해당 릴레이션을 대표할 수 있는 적절한 키를 단 하나로 정해야 합니다. 그렇다면 속성의 집합에 따라 매우 다양한 키가 존재하는데 이 중에서 과연 어떤 후보키를 기본키로 정해야 할까요? 여기에는 몇 가지 기준이 존재합니다.

     

     

    기본키의 설정 조건

    널 값을 가질 수 있는 속성이 포함된 후보키는 기본키로 부적합하다.

     위의 예에서 저는 후보키로 학번, (이름, 주소) 이렇게 두 가지를 선택했다고 가정합시다. 이 두 가지 중 한 가지를 기본키로 선택해야 할 텐데 과연 어떤 게 더 좋은 선택일까요? 위의 조건에 따라 (이름, 주소)는 기본키로 선정되어서는 안 됩니다. 첫 번째 사진을 보면 최영호 학생의 주소 값이 NULL인 것을 확인할 수 있는데요. 개념상 (이름, 주소)가 각 투플을 유일하게 구분 지을 수 있더라도 주소값이 NULL로 입력될 수 있으므로 이 속성 조합은 기본키로 활용되어서는 안 됩니다. 이후에 동명이인의 최영호라는 학생이 주소값을 NULL로 하여 새로운 투플로 저장될 경우 이 둘을 구분지을 수 없기 때문이죠.

     

    값이 자주 변경될 수 있는 속성이 포함된 후보키는 기본키로 부적합하다.

     만약 방금 언급한 (이름, 주소) 속성 집합에서 주소가 NULL값을 가질 수 없다고 가정해 봅시다. 그렇다 하더라도 이 속성 집합을 기본키로 정하기에는 분명히 적절하지 못한 측면이 있습니다. 왜냐하면 주소 값이 자주 변할 수 있기 때문입니다. 이렇게 기본키를 이루는 속성 하나가 자주 변하게 된다면 매번 해당 투플의 속성을 수정할 때마다 기본키의 자격을 만족해야 하는지를 검사해야 합니다. 해당 릴레이션에 데이터 수가 엄청 많아진다면 시스템에 굉장한 비효율을 초래하게 되겠죠.

     

    단순한 후보키를 기본키로 선택한다.

     현대의 데이터베이스 시스템은 컴퓨팅 시스템을 기반으로 합니다. 이것은 컴퓨터의 연산을 통해 데이터베이스를 관리한다는 것을 의미합니다. 기본키를 이용하여 데이터베이스 상에서 특정한 데이터를 찾아낸다는 것은 이 기본키를 이용해서 연산을 하는 것과 같습니다. 그렇다면 당연히 속성이 여러 개로 이루어진 후보키 보다는 단 하나의 속성만으로 이루어진 후보키를 기본키로 선택하는 것이 보다 좋은 선택입니다. 어느 두 투플을 구분 지을 때 여러 개의 속성을 비교 연산하기보다 단 하나의 속성만을 비교 연산한다면 전체 시스템의 성능이 빨라질 테니까요.

     결국 이 기준들을 따른다면 위의 예에서 기본키로서 가장 좋은 선택은 바로 '학번'입니다.

     

     

    외래키

     외래키는 위에서 살펴본 키들과는 조금 다른 특성을 지니고 있습니다. 지금까지 키에 대해 관계 데이터 모델을 맥락으로 하여 설명하였는데요. 이 외래키는 바로 이 관계 데이터 모델에서 핵심적인 역할을 수행합니다. 어느 한 릴레이션이 다른 릴레이션과 관계를 맺으며 참조하기 위해 사용되는 키이기 때문입니다. 즉 외래키란 어느 한 릴레이션에서 다른 릴레이션의 기본키를 참조하는 속성 또는 속성들의 집합을 의미합니다. 예를 들어 위의 릴레이션과 더불어 다음과 같은 과제 릴레이션이 있다고 가정해 보겠습니다.

    외래키를 통해 관계를 맺고 있는 학생 릴레이션과 과제 릴레이션

     과제 릴레이션에서 '수행 학생'이라는 속성은 학생 릴레이션의 기본키인 학번 속성을 참조하며 학생 릴레이션과 관계를 맺고 있습니다. 여기서 중요한 점은 과제 릴레이션에서의 외래키명이 학생 릴레이션의 기본키명과 같을 필요는 없다는 점입니다. 다만 '참조하는' 릴레이션에서의 외래키는 '참조되는' 릴레이션의 기본키를 참조하기만 하면 됩니다.

     

    참고

    데이터베이스 개론 2판, 김연희, 한빛아카데미

     

    'Database' 카테고리의 다른 글

    [Database] 조인(JOIN)의 종류(MySQL 기준)  (0) 2022.09.01

    댓글

Designed by Tistory.