타입을 더 정밀하게 제어하는 세 가지 핵심 기법을 정리합니다.
1. 리터럴 타입 (Literal Types)
변수에 들어올 수 있는 값을 특정 값으로 한정하는 타입입니다.
const vs let의 타입 추론 차이
const userName1 = "Bob"; // 타입: "Bob" (리터럴 타입)
let userName2 = "Tom"; // 타입: string
const는 값이 변하지 않으므로 TypeScript가 "Bob"이라는 리터럴 타입으로 추론합니다. 반면 let은 값이 바뀔 수 있어 넓은 string 타입으로 추론됩니다.
문자열 리터럴 타입 활용
type 별칭과 함께 사용하면 허용 가능한 값을 명확히 제한할 수 있습니다.
type Job = "police" | "developer" | "teacher";
interface User {
name: string;
job: Job;
}
const user: User = {
name: "Bob",
job: "police" // ✅ OK
// job: "singer" // ❌ Error — Job에 없는 값
}
숫자 리터럴 타입
문자열뿐 아니라 숫자도 리터럴 타입으로 제한할 수 있습니다.
interface HighSchoolStudent {
name: string;
grade: 1 | 2 | 3; // 1, 2, 3만 허용
}
💡 리터럴 타입은 "이 변수에는 이 값들만 올 수 있다"는 제약을 컴파일 단계에서 강제합니다. 오타나 잘못된 값 할당을 사전에 방지할 수 있습니다.
2. 유니온 타입 (Union Types)
| 연산자로 여러 타입 중 하나를 허용하는 타입입니다.
interface Car {
name: "car";
color: string;
start(): void;
}
interface Mobile {
name: "mobile";
color: string;
call(): void;
}
function getGift(gift: Car | Mobile) {
console.log(gift.color); // ✅ OK — 둘 다 가지고 있는 프로퍼티
gift.start(); // ❌ Error — Car에만 있는 메서드
}
유니온 타입의 변수에서는 두 타입 모두에 존재하는 프로퍼티만 바로 접근할 수 있습니다. 한쪽에만 있는 프로퍼티를 사용하려면 타입을 좁혀야 합니다.
식별 가능한 유니온 (Discriminated Union)
두 인터페이스에 공통으로 존재하는 리터럴 타입 프로퍼티를 기준으로 분기하면, TypeScript가 타입을 자동으로 좁혀줍니다.
function getGift2(gift: Car | Mobile) {
console.log(gift.color);
if (gift.name === "car") {
gift.start(); // ✅ OK — 이 블록 안에서 gift는 Car
} else {
gift.call(); // ✅ OK — 이 블록 안에서 gift는 Mobile
}
}
💡 name 프로퍼티가 "car" 또는 "mobile" 리터럴 타입이기 때문에, 조건문으로 분기하면 TypeScript가 해당 블록 안에서의 타입을 정확히 추론합니다. 이것을 **타입 가드(Type Guard)**라고 합니다.
3. 교차 타입 (Intersection Types)
& 연산자로 여러 타입을 모두 만족하는 타입을 만듭니다. 유니온이 "A 또는 B"라면, 교차는 "A 그리고 B"입니다.
interface Car2 {
name: string;
start(): void;
}
interface Toy2 {
name: string;
color: string;
price: number;
}
const toyCar: Toy2 & Car2 = {
name: "타요",
start() {},
color: "blue",
price: 1000
}
Toy2 & Car2이므로 두 인터페이스의 프로퍼티를 모두 가져야 합니다. 하나라도 빠지면 에러가 발생합니다.
유니온 vs 교차 비교
구분 유니온 (|) 교차 (&)
| 의미 | A 또는 B | A 그리고 B |
| 필요 프로퍼티 | 공통 프로퍼티만 바로 접근 가능 | 모든 프로퍼티를 반드시 포함 |
| 사용 시점 | 여러 타입 중 하나를 받을 때 | 여러 타입을 합쳐 하나로 만들 때 |
| 예시 | Car | Mobile | Toy2 & Car2 |
한눈에 보기
기능 문법 설명
| 문자열 리터럴 | type Job = "police" | "developer" | 특정 문자열만 허용 |
| 숫자 리터럴 | grade: 1 | 2 | 3 | 특정 숫자만 허용 |
| 유니온 타입 | Car | Mobile | 여러 타입 중 하나 |
| 타입 가드 | if (gift.name === "car") | 조건문으로 타입 좁히기 |
| 교차 타입 | Toy2 & Car2 | 여러 타입을 모두 만족 |
'프론트' 카테고리의 다른 글
| TypeScript 제네릭(Generic) (0) | 2026.04.11 |
|---|---|
| TypeScript 클래스(Class) (0) | 2026.04.11 |
| TypeScript 함수 타입 (0) | 2026.04.11 |
| TypeScript 인터페이스(Interface) (0) | 2026.04.11 |
| TypeScript 기초 타입 정리 (0) | 2026.04.11 |