SQLD에서 이론파트 내는 것 중에서 꽤 자주 보이는게 식별자이다. 말 그대로 어떤 대상(개체, 정보 등)을 고유하게 구분하고 식별하는 데 사용되는 이름이나 기호를 일컫는다. 이놈 이름 짓는게 내 포켓몬 작명하는것만큼 어렵다. (김부추가 막 지은 이름같지만 아님) 제육쌈밥이 막 지은 이름이 아니라고요?
식별자의 분류법
일단 여기에 네 가지의 분류 기준이 나올건데, 그래서 분류 카테고리가 총 8개가 나온다. 근데 여기서 미리 말씀드리자면 어떤 식별자가 총 8개 카테고리 중 하나에'만' 속하는 게 아니라 여기서는 이거, 여기서는 이거 이런 식으로 4개 카테고리에 각각 속하는 분류가 있다.
대표성에 따른 분류-주식별자 vs 보조식별자
주식별자와 보조식별자는 엔터티 안에 있는 각 인스턴스들을 구별할 수 있는가에 따라 나눈다. 그러니까 포켓몬 도감으로 치자면 도감 번호랑 이름이 되겠다. 주식별자 중에는 남의 집 엔터티에 참조 관계(FK)로 가는 경우도 있는데, 이렇게 되면 그 식별자는 남의 집 입장에서는 외부식별자가 된다. 이건 밑에서 한번 더 얘기해드림.
그럼 보조식별자는요? 보조식별자는 인스턴스들을 구별할 수는 있지만 대표성을 갖지는 않는다. 그래서 남의 집에 FK로 가지는 못 한다. 생각해봅시다. 포켓몬의 타입으로 포켓몬들을 구별할 수는 있지만 특정 타입이 포켓몬을 대표하지는 않잖아요. 타입이 17갠가 18갠가 그래 지금… 아무튼 보조식별자는 주식별자로 쓸 수 있는데 굳이 쓸 필요성을 못 느껴서 안 쓴 케이스라고 보면 된다.
목적에 따른 분류-내부식별자 vs 외부식별자
어르신들이나 나이 좀 있으신 분들이 가끔 그런 얘기 할 때가 있다. 사위는 백년손님. 아니 그건 며느리도 마찬가지 아니냐. 아무튼… 사위가 뭔데요? 여자 형제(혹은 이 글을 읽는 독자가 여성이라면)가 결혼하면 남편이 생기잖아요? 그 남편을 여자 형제의 부모님이 사위라고 함. 남편은 부모님을 장인, 장모님이라고 하고 좀 고상하게는 빙장님 빙모님 하기도 합니다.
근데 갑자기 사위 얘기가 왜 나와요? 가족이 하나의 엔터티라고 할 때, 사위는 외부식별자이다. 뭔 소리요? 들어봐요. 나랑 엄빠 남동생은 가족이잖아요. 그러니까 우리 집 엔터티에서 나랑 엄빠 남동생은 내부식별자다. 만약에 나나 남동생이 결혼 상대를 데려온다면(그럴 일이 있을지는 모르겠다만) 그 결혼 상대는 다른 집안의 아들/딸이 우리 집으로 가족이 되러 오는거니까 외부식별자다. 식별자가 어떤 엔터티 안에서 나온거면 내부식별자, 반대로 남의 엔터티에서 FK로 오는 경우는 외부식별자다.
속성 수에 따른 분류-단일식별자 vs 복합식별자
그 단백질을 보면 아미노산을 줄줄이 엮고 접어서 3차구조까지 만들면 고대로 쓰는 게 있고, 3차구조 만든걸 또 합쳐서 4차구조까지 만들어야 쓰는 게 있다. 3차구조 만들어서 혼자 일할 수 있는 애는 단일식별자, 4차구조까지 만들어서 다른 애랑 묶어야 하는 애는 복합식별자다. 보통 4차구조까지 만들게 되면 덩어리 한 두세개는 모여야 일을 할 수 있게 되는데(항체도 4량체다), 이거랑 비슷하게 복합식별자는 속성이 두 개 이상 모여있다.
왜 이렇게까지 하는거예요? 걔들은 그래야 일을 합니다. 아니 단백질 말고요. 그러니까 걔들도 혼자서는 식별자 일을 못 하니까 모이는거예요.
본질에 따른 분류-본질식별자 vs 인조식별자
서울 밖으로 나갈 일이 잘 없어서 다른데는 어떤지 모르겠는데, 서울 버스 정류장에는 정류장 아이디라는 게 있다.

이거 네이버 지도에서 찍은거긴 한데 네이버 지도에만 있는거 아니고 정류장마다 다 붙어있는거다. 서울 사시는 분들은 집 근처 정류장 함 가보십쇼.
저 번호에도 나름 체계가 있어서 앞에 두자리는 행정구고, 0이 붙으면 버스 전용 차로라고 한다. 그니까 광진구에 있는 모든 버스정류장은 앞자리 두개가 05고, 저 정류장은 횡단보도 가운데에 있고 도로에 파란 선(버스 전용 차로)이 있다. 근데 뜬금없이 웬 버스정류장? 쟤가 인조식별자니까요.
본질식별자는 업무에 이미 존재하는 속성으로 만들어지는 식별자다. 아마 버스정류장이라면 이름이 되겠지만... 유감스럽게도 이름은 주식별자로 쓸 수 없다. 왜죠? 같은 이름의 정류장이 두 개 있을수도 있으니까. 저기 예시로 든 군자교입구도 이름 같은 정류장이 두 개다. 그럼 둘이 뭔 차이예요? 가는 방향이 다릅니다. 하나는 중곡동쪽으로, 하나는 장한평쪽으로 간다.
근데 일반인들도 그렇고 행정일 하시는 분들도 그렇고 방향으로 구별할 수 있겠어요? 막말로 정류장 아이디 없이 군자교입구에서 장한평역 방향 가는 370 타세요 하면 반대방향으로 가는 사람 생깁니다. 그리고 저걸로 쿼리 치기가 정말 빡세요. 왜죠? 아니 광진구에 있는 모든 버스정류장 이름이 군자로 시작하질 않아요 님들아… 막말로 광진구에 동이 몇갠데… 광진구에 군자동만 있는거 아닙니다… 주민센터로만 정류장 매겨도 화양동 주민센터, 중곡동 주민센터, 구의동 주민센터, 자양동 주민센터 이렇게 나오는데 저 아이디 없이 이름만으로 정류장 찾으려면 쿼리에 정규식까지 짜느라 님들 머리가 터져요.
그래서 인조식별자는 뭐냐, 정류장 이름으로 찾기 힘드니까 우리가 특정 규칙을 갖는 정류장 아이디를 만들자 이거다. 정류장명이 같아도 방향이 다르면 아이디가 다르기떄문에 예시로 든 군자교입구도 하나는 002, 하나는 001이다. 지도 앱에도 아이디 다 나오니까 가는 방향만 알면 아이디가 몇 번인 정류장에서 370 타면 되는구나 할 수 있고, 쿼리 짤때도 광진구 버스정류장 찾아주셈 할거면 05로 시작하는 정류장 찾으면 된다.
주식별자의 특징
주식별자의 특징은 유일성, 최소성, 불변성, 존재성에 있다. 이게 다 뭐여?
1. 유일성: 주식별자에 의해 각 엔터티 내의 인스턴스들을 유일하게 구분할 수 있어야 한다. 내가 항상 하는 얘기가 '이름은 단독으로 PK가 될 수 없다'이다. 왜죠? 동명이인 있잖아요. 나야 뭐 그렇게 흔한 성은 아니지만 서울 가서 김아무개씨만 찾아도 동명이인 두세명은 나올거다. 서울 가서 김서방 찾기라는 말이 괜히 있는 게 아니다.
2. 최소성: 주식별자를 구성하는 속성의 수는 유일성을 만족하는 최소의 수가 되어야 한다. 그니까 쓸데없이 사족 달지 말라는 얘기다. ID만으로 식별이 가능한데 전화번호까지 넣지 말자, 이 얘기. 이걸 위반해서 부분함수 종속이 생겼다고요? 축하드립니다! 2차 정규화로 찢으시면 됩니다!
3. 불변성: 주식별자가 지정되는 그 식별자의 값은 변하지 않아야 한다. 여기서 이름이 PK가 될 수 없는 이유가 또 나온다. 개명하면 이름 바뀌잖아요. 그럼 안 바뀌는 것도 있나요? 어떤 사이트 가입할 때 만드는 아이디는 탈퇴하고 다시 만들지 않는 이상 못 바꾼다.
4. 존재성: NULL이면 안된다. 그니까 얘가 존재하고 있다는 게 명확해야 한다. SQL은 응 아니 몰라 세가지로 돌아가고 널은 몰라에 포함된다. 주식별자가 널이라는 건 얘를 뭔가 대표할만한 게 있는데 그게 뭔지 모른다는 피카츄 전기세 밀렸다고 한전에서 전화오는 소리다. 그래서 제약조건에 PK 걸면 UNIQUE&NOT NULL이 알아서 따라온다. 왜죠? 주식별자의 특성을 한마디로 요약하자면 UNIQUE&NOT NULL이니까요.
주식별자의 도출 기준
주식별자를 도출할때는 일단 이름은 안된다. 위에도 썼지만 동명이인이 있을 수도 있고, 개명을 하면 바뀌기도 하고, 우리야 뭐 주변에서 길어봐야 4자까지지만 외국은 뭐 루이 윌리암스 세바스찬 주니어 3세 이런식으로 이름들이 다 긴데 이걸 주식별자로 한다? 어디서 O(n) 늘어나는 소리 안 들려요?
그리고 다른 기준 하나는 바로 '업무에 쓰이는 속성들 중에서도 자주 쓰이는 속성'으로 한다는거다. 포켓몬 도감에서 포켓몬의 주식별자로는 도감번호, 이름, 폼체인지 여부(뭐 예를 들자면 알로라이츄라던가)정도지 종족값 총합 이딴걸로 안 한다. 아니 막말로 여기서 라이츄 종족값 외우는 사람 있음? 그리고 리전폼이랑 걍 라이츄랑 종족값 분배만 다르고(알로라이츄가 좀더 특공에 쏠림) 총합은 같다.
마지막은 인조식별자에 대한 얘기. 본질식별자가 길어서 만든다, 이건 좋다. 좋은데 그래서 인조식별자를 만드는데 너무 많은 속성이 포함되면 안된다. 인조식별자를 만드는 데 너무 많은 속성이 포함되면 처음 보는 사람 입장에서는 수헬리벨붕탄질산플네보다 더 머리터지는 무언가가 된다. 쿼리짜는것도 지옥이겠구만...
식별자/비식별자 관계
아니 아직도 안 끝났어요? 다 왔으니까 여기까지만 보고 가셔들. 이것도 중요한거임.

이거 한방이면 이해 쏙 된다. 그렇다고 그림만 보지 말고...
식별자 관계는 부모 엔터티에서 자식 엔터티로 식별자를 상속했고(자식 엔터티 입장에서는 FK가 된다), 그 주식별자가 자식 엔터티의 주식별자로 들어가는 경우 식별자 관계라고 한다. 비식별자 관계는 반대로 부모 엔터티에서 상속받은 식별자가 자식 엔터티의 비식별자로 들어가면 그건 비식별자 관계다. 위 예기의 도감 번호 역시 비식별자로 들어가기 때문에 비식별자 관계. ERD를 IE로 그린다면 비식별자 관계는 점선, 식별자 관계는 실선이다.
부모 엔터티와 자식 엔터티가 식별자 관계에 있는 경우, 자식 엔터티는 약한 엔터티가 된다. 왜죠? 부모가 있어야만 쟤도 존재할 수 있으니까요. 반대로 비식별자 관계라면 굳이? 상속을? 제가요? 상태가 된다. 주식별자로 사용 가능하지만 독립적인 주식별자 설정이 필요한 경우에도 비식별자 관계로 상속되는데, 이건 의외로 상속 하는 쪽이 아니라 상속 받는 쪽에서 정한다. 뭔 한정 승인이여?
식별자 관계차수
그 전에 관계 얘기하면서 차수 얘기했던거 기억나시죠? 1:1 1:다 다:다. 그게 식별자간에도 존재한다.
자식 엔터티가 부모 엔터티의 주식별자만을 상속받아서 주식별자로 사용하는 경우 1:1 관계이다. 이게 뭔 소리고? 예를 들어서 도서관에 소장중인 책 정보를 기록하는 DB가 있고, 이 DB에서 주식별자가 책의 분류 코드라고 해보자. 뭐 800–01 이런 식으로 붙였다 치면, 책의 분류 코드를 FK로 받아서 PK로 쓰는 엔터티는 1:1관계이다. 그리고 1:N은 책의 분류코드를 FK로 받아서 다른 무언가랑 같이 조합해서 쓰는 경우이다.
모든것은 과유불급
뭐든지 남발하면 안 좋은데, 이건 식별자/비식별자 관계도 마찬가지다. 식별자 관계를 남발하게 되면

식별자 관계일때는 PK로 가니까 저기 저 가로선 위에 쓴단말이죠. 근데 저게 식별자 상속이 계속되면 쟤가 있어야->쟤들이 있어야가 되기 때문에 ERD가 진분수에서 가분수가 된다. 비교해야 하는 연산이 많아지니까 일단 관리 효율성이 떨어지고, 중복률이 올라가고, 이해도가 떨어진다.
반대로 비식별자 관계를 남용하게 되면 뭐 하나 할래도 조인을 해야 한다. 그러니까 비식별자 관계를 남발하게 되면 뭐 하나 찾으려면 남의 집 테이블까지 연결해야 하기 때문에 성능이 떨어지고 소요시간이 훅 올라간다. OS가 리눅스인데 터미널에서 한다고요? 쿼리 치는 사람 혈압도 같이 올라갈 것이다.
이게 뭐 정답이 있는 건 아니지만, 본인이 추구하는 방향성에 맞춰서 고려해야 할 필요는 있다.
'Coding > 코딩잡담' 카테고리의 다른 글
| 스키마 (0) | 2025.11.14 |
|---|---|
| Select문에도 순서가 있다 (0) | 2025.11.13 |
| 롤업, 큐브, 그리고 그루핑 셋 (0) | 2025.11.13 |
| NULL이란 무엇인가 (0) | 2025.11.12 |
| 속성과 관계 (0) | 2025.11.11 |