속성과 도메인: 값의 의미와 품질
속성의 분류와 도메인·파생 속성·NULL 허용의 업무 의미를 데이터 품질과 제약조건 관점에서 정리합니다.
핵심 요약
속성의 분류와 도메인·NULL·파생 속성의 설계 원칙을 데이터 품질 관점에서 정리한다.
핵심 질문
- 속성과 도메인: 값의 의미와 품질를 실제 업무 사례에서 어떤 기준으로 판별하는가?
- 한 행이 나타내는 업무 사실과 유일성·필수성·변경 가능성은 무엇인가?
- 잘못 모델링하면 어떤 중복·이상 현상·변경 영향이 발생하는가?
- 여러 설계안 중 업무 의미와 변경 용이성을 가장 잘 보존하는 안을 어떻게 고르는가?
학습 목표
- 기본·설계·파생 속성과 단순·복합 속성을 구분한다.
- 도메인이 데이터 품질에 미치는 영향을 설명한다.
개념 지도
업무 사실 → 엔터티와 행 단위 → 속성·도메인 → 관계·카디널리티 → 제약
핵심 내용
속성은 엔터티 인스턴스를 설명하는 최소 의미 단위다. 한 속성은 한 업무 의미를 가져야 하고, 같은 종류의 값이 들어오도록 도메인을 정한다. 도메인은 데이터 타입만이 아니라 길이, 허용 범위, 형식, 기본값과 제약조건까지 포함하는 값의 집합이다.
- 기본 속성: 업무에서 본래 수집하는 값(주문일시)
- 설계 속성: 모델 구현을 위해 만든 값(주문번호)
- 파생 속성: 다른 값으로 계산되는 값(주문합계)
파생 속성은 조회를 빠르게 할 수 있지만 원천 값과 불일치할 위험이 있다. 저장할 때는 계산 규칙, 갱신 시점, 책임 주체를 함께 정해야 한다. NULL은 미정·해당 없음처럼 값이 없음을 나타내며 0이나 공백과 다르다.
흔한 오해와 주의점
- 속성은 더 이상 의미 있게 분리할 필요가 없는 업무 단위이지, 무조건 물리적으로 가장 작은 문자열은 아니다.
- 복합 속성을 여러 컬럼으로 나누는 판단은 검색·정렬·검증 등 업무 사용 방식을 따른다.
- 파생 속성은 언제나 나쁜 것이 아니지만 무결성 유지 비용을 동반한다.
문항 풀이 보강: 속성의 성질·명명·도메인
속성은 엔터티의 인스턴스를 설명하며 한 속성에는 한 가지 업무 의미가 들어가야 한다. 일반적으로 업무에서 관리할 필요가 있고, 주식별자에 함수적으로 종속되며, 같은 의미의 값이 반복 그룹으로 저장되지 않아야 한다.
| 분류 기준 | 종류 | 예 |
|---|---|---|
| 발생 원천 | 기본 / 설계 / 파생 | 원금 / 주문번호 / 계산이자 |
| 구성 | 단일 / 복합 | 성별 / 주소 |
| 값의 수 | 단일값 / 다중값 | 생년월일 / 여러 전화번호 |
원금과 이자율로 계산한 이자를 저장하면 파생 속성이다. 조회는 빨라질 수 있지만 원금이나 이자율 변경 시 함께 갱신해야 하므로 계산 기준과 동기화 시점이 필요하다.
도메인은 데이터 타입만 뜻하지 않는다. 허용 범위, 길이, 형식과 제약까지 포함한다.
amount NUMBER(12,2) CHECK (amount >= 0)
product_name VARCHAR2(20) NOT NULL
속성 이름의 기준
- 업무에서 사용하는 이름을 쓴다.
- 서술식으로 지나치게 길거나 의미가 모호한 약어를 피한다.
- 엔터티 안에서 유일한 이름을 사용한다.
- 동일 의미 속성은 모델 전체에서 가능한 한 같은 이름과 도메인을 사용한다.
NULL 속성을 모델링할 때 구분할 업무 상태
NULL은 단순히 “값이 없다”가 아니라 서로 다른 업무 원인을 가릴 수 있습니다.
| 상태 | 예 | 모델링 판단 |
|---|---|---|
| 아직 모름 | 배송 전 실제 배송일 | NULL 허용 가능 |
| 해당 없음 | 법인이 아닌 개인의 법인등록번호 | 별도 유형·서브타입 검토 |
| 입력 누락 | 필수 연락처 미입력 | NOT NULL 또는 검증 필요 |
| 보안상 비공개 | 사용자가 공개를 거부한 값 | 동의 상태 컬럼과 분리 검토 |
서로 다른 상태를 모두 하나의 NULL로 저장하면 “미입력”과 “해당 없음”을 구분할 수 없습니다. 반대로 의미 없는 기본값 0, 'N/A', '99991231'을 넣으면 실제 값과 구분이 어려워지고 집계·정렬·제약이 왜곡됩니다.
CREATE TABLE customer (
customer_id NUMBER PRIMARY KEY,
customer_type VARCHAR2(10) NOT NULL,
corporation_no VARCHAR2(20),
CONSTRAINT customer_c1 CHECK (
(customer_type = 'CORP' AND corporation_no IS NOT NULL)
OR
(customer_type <> 'CORP' AND corporation_no IS NULL)
)
);
시험에서는 필수성(Optionality), 업무상 해당 여부, 도메인, 기본값을 함께 보고 NULL 허용이 업무 의미를 정확히 표현하는지 판단합니다.
문제에 적용하는 순서
“계산하여 저장”, “합계·잔액·나이”는 파생 속성 가능성을 본다. “값의 범위·길이·형식”은 도메인, “원래 업무에서 수집”은 기본 속성, “식별을 위해 인위적으로 부여”는 설계 속성이다.
속성 분류를 실제 Column으로 연결하기
고객번호 기본·식별 속성
생년월일 기본 속성
나이 파생 속성(기준일에 따라 계산)
주소 복합 속성 후보(우편번호·시도·상세주소)
전화번호 목록 다중값 속성 → 별도 고객전화 엔터티 후보
파생값을 저장하면 조회는 쉬워지지만 원천값이 바뀔 때 동기화가 필요하다. 나이처럼 시간에 따라 변하는 값은 저장보다 생년월일과 기준일에서 계산하는 편이 일관적이다.
도메인이 보장할 것
도메인은 단순 데이터 타입이 아니라 허용 범위·형식·단위·코드 의미를 포함한다.
status_code VARCHAR2(10) NOT NULL
CHECK (status_code IN ('READY','PAID','CANCEL'))
금액의 통화, 비율의 단위, 날짜의 Time Zone을 속성 이름과 정의에 명시한다. 같은 상태코드 이름을 주문과 고객에서 서로 다른 의미로 사용하면 동음이의어 문제가 생긴다.
원자성은 업무 문맥 기준
주소 전체가 항상 한 번에 출력만 된다면 문자열 하나로 볼 수도 있지만 지역별 검색·우편번호 검증·주소 이력이 필요하면 구성 요소로 분리한다. 원자성은 DBMS 타입의 최소 크기가 아니라 업무에서 더 이상 분해해 사용할 필요가 없는 수준이다.
품질 체크
- 속성마다 한 가지 의미와 출처가 있는가?
- NULL이 미입력·해당 없음·알 수 없음 중 무엇인지 정의했는가?
- 코드·단위·길이·정밀도와 유효기간을 정했는가?
- 파생 속성의 계산식과 기준 시점을 재현할 수 있는가?
사례를 판별하는 순서
- 모델이 표현해야 하는 업무 사실과 행 단위(Grain)를 한 문장으로 정의합니다.
- 각 인스턴스를 유일하게 식별할 수 있는 후보와 변경 가능성을 확인합니다.
- 속성이 어느 사실에 종속되는지와 관계의 필수성·카디널리티를 확인합니다.
- 중복 저장으로 삽입·갱신·삭제 이상이 생기는지 검토합니다.
- 물리 성능을 이유로 구조를 바꿀 때 원천 데이터와 동기화·복구 규칙을 함께 설계합니다.
모델 품질 확인표
- 같은 업무 사실이 여러 곳에 중복 저장되지 않는가?
- 이름과 도메인이 한 가지 의미로 사용되는가?
- PK·FK가 실제 업무 관계와 선택성을 정확히 표현하는가?
- 현재 화면이나 프로세스에 과도하게 종속되지 않는가?
- 정규화와 성능 설계의 이유를 측정 가능한 근거로 설명할 수 있는가?
마지막 점검
- 화면의 입력 항목이나 현재 프로세스를 그대로 엔터티·관계로 옮기지 않습니다.
- 한 행의 업무 사실, 후보 식별자와 함수 종속성을 먼저 확정합니다.
- 중복과 비일관성을 만들면서 조회 편의만 얻는 설계를 정답으로 선택하지 않습니다.
- 반정규화와 물리 설계는 측정된 성능 문제와 동기화·복구 대책이 있을 때 적용합니다.
복습 문제
- 생년월일로 계산 가능한 나이를 저장할 때 필요한 관리 규칙은 무엇인가?
- 금액 컬럼의 데이터 타입만 정하면 도메인 정의가 끝나는가?
- 이 개념을 실제 업무 사례에서 판별할 수 있는가?
- 한 행의 업무 의미와 식별자를 설명할 수 있는가?