2025 / 02 / 26
오늘 수업 시간에는 enum과 타입 추론하는 방법을 배웠습니다.
시스템의 상태를 관리할 떄 편하게 사용할 수 있는 부분이라고 합니다.
저는 써본 적이 없어서 잘은 모르겠지만, 자주 사용된다고 하니까 정리해보겠습니다.
Enum(열거형 타입)
- 특정 값들의 집합을 정의하여 관리할 수 있도록 해주는 데이터 타입입니다.
- 주로 상수 값들을 한곳에 모아두고, 가독성 높은 코드 작성을 위해 사용합니다.
- JavaScript에서는 enum 기능이 내장되어 있지 않지만, TypeScript에서는 enum을 제공하여 코드의 안정성과 가독성을 높여줍니다.
- Enum을 사용하면 특정 값들이 서로 연관되어 있음을 명확하게 표현할 수 있습니다.
enum State { DONE = "Done", // 완료 LOADING = "LOADING", // 로딩 중 INITIAL = "INITIAL", // 초기 상태 ERROR = "ERROR" // 에러 발생 }
1. 가독성 향상
- 특정 값들이 무엇을 의미하는지 쉽게 파악할 수 있습니다.
2. 안전성
- 타입이 고정되어 있어서 실수로 잘못된 값이 할당되지 않도록 막아줍니다.
3. 유지보수 용이
- 값을 변경할 때 한 곳에서만 수정하면 되므로 유지보수가 용이합니다.
1. 상태 관리
- runWork( ) 함수에서 API 요청 상태를 문자열 값으로 관리하는 예시입니다.
- 문자열을 직접 사용하는 것보다 Enum을 사용하면 가독성이 높아지고 실수로 잘못된 값을 입력하는 것을 방지할 수 있습니다.
function runWork() { let state = "INITIAL"; try { state = "LOADING"; // 로딩중 // 시간 경과 후... state = "DONE"; // 완료 } catch (error) { state = "ERROR"; // 에러 } finally { return state; } } console.log(runWork() === "DONE"); // true
2. Enum 사용
- State Enum을 사용하여 상태를 관리합니다.
- 각 상태를 명확히 표현할 수 있고, 실수로 잘못된 값을 사용하지 않도록 도와줍니다.
// Enum 정의 enum State { DONE = "Done", LOADING = "LOADING", INITIAL = "INITIAL", ERROR = "ERROR" } function runWork2() { let state = State.INITIAL; // 초기 상태 try { state = State.LOADING; // 로딩 중 // 시간 경과 후... state = State.DONE; // 완료 } catch (error) { state = State.ERROR; // 에러 발생 } finally { return state; } } console.log(runWork2() === State.DONE); // true
- Enum을 활용하면 여러 상태나 값을 효율적으로 처리할 수 있습니다.
- apiStatus라는 함수에서 Enum 값을 받아서, 각 상태에 맞는 로직을 처리할 수 있습니다.
- switch 문을 사용해 각 상태별로 다른 처리를 할 수 있습니다.
function apiStatus(status: State) { switch (status) { case State.DONE: console.log("성공"); break; case State.INITIAL: console.log("초기 상태"); break; case State.ERROR: console.log("에러 발생"); break; case State.LOADING: console.log("로딩 중"); break; default: console.log(status); } } // 함수 호출 apiStatus(State.DONE); // 성공 apiStatus(State.INITIAL); // 초기 상태 apiStatus(State.ERROR); // 에러 발생 apiStatus(State.LOADING); // 로딩 중
- Enum은 숫자 값으로도 정의할 수 있습니다.
- 첫 번째 값은 0부터 시작하며, 이후 값들은 자동으로 증가합니다.
enum State { DONE, // 0 LOADING, // 1 INITIAL, // 2 ERROR // 3 } console.log(State.DONE); // 0 console.log(State.LOADING); // 1 console.log(State.INITIAL); // 2 console.log(State.ERROR); // 3
- 숫자 값이 자동으로 할당되며, 필요에 따라 특정 값부터 시작할 수 있습니다.
enum State { DONE = 1, // 1부터 시작 LOADING, // 2 INITIAL, // 3 ERROR // 4 } console.log(State.DONE); // 1 console.log(State.LOADING); // 2 console.log(State.INITIAL); // 3 console.log(State.ERROR); // 4
배달 주문 상태 관리하기
- 주문 상태를 나타내는 orderStatus라는 enum 생성합니다.
- PENDING, PREPARING, ONTHEWAY, DELIVERED 네 가지 상태를 가집니다.
- 각각 주문 접수중, 준비중, 배송중, 배달완료를 의미합니다.
- 현재 상태를 한글로 알려주는 updateOrderStatus 함수 생성합니다.
- updateOrderStatus 함수는 orderStatus를 파라미터로 받아서 주문 상태를 출력합니다.
enum orderStatus { PENDING, PREPARING, ONTHEWAY, DELIVERED, } function updateOrderStatus(state: orderStatus) { switch (state) { case orderStatus.PENDING: console.log("접수중"); break; case orderStatus.PREPARING: console.log("준비중"); break; case orderStatus.ONTHEWAY: console.log("배송중"); break; case orderStatus.DELIVERED: console.log("배달완료"); break; default: console.log(state); } } updateOrderStatus(orderStatus.PENDING); updateOrderStatus(orderStatus.PREPARING); updateOrderStatus(orderStatus.ONTHEWAY); updateOrderStatus(orderStatus.DELIVERED);
- 타입 추론은 타입스크립트의 중요한 특징 중 하나로, 변수나 함수의 타입을 명시적으로 지정하지 않아도 자동으로 추론하여 타입을 결정해주는 기능입니다.
- 타입을 명시적으로 지정하지 않아도 TypeScript가 변수나 값에 적합한 타입을 추론하여 코드의 안정성을 높여줍니다.
- 타입 추론을 잘 활용하면 코드 작성 시 타입을 명시하지 않아도 되는 경우가 많아지며, 코드의 가독성과 효율성이 높아집니다.
타입스크립트에서는 변수에 값을 할당하는 순간, 값에 맞는 타입을 자동으로 추론합니다.
① 기본 데이터 타입
- stringType, booleanType, numberType 변수는 각각 "string", true, 30 값에 의해 자동으로 타입이 결정됩니다.
- TypeScript는 해당 값을 보고 string, boolean, number 타입을 추론합니다.
let stringType = "string"; // 타입은 string으로 추론됨 let booleanType = true; // 타입은 boolean으로 추론됨 let numberType = 30; // 타입은 number로 추론됨
- const로 선언된 변수는 값이 변경되지 않습니다.
- 해당 변수는 고정된 값의 타입을 갖게 됩니다.
① 상수 선언
- const로 선언된 변수는 리터럴 타입을 가지며, 해당 값이 변경되지 않음을 보장합니다.
const constStringType = "const String"; // 타입은 'const String'으로 고정됨 const constBooleanType = true; // 타입은 true로 고정됨
- 속성에 값을 할당할 때 그 값을 바탕으로 타입을 추론합니다.
- 객체를 const로 선언하면 객체의 구조까지 리터럴 타입이 고정됩니다.
① 객체 타입 추론
- idol은 name이 string, age가 number인 객체로 추론됩니다.
- idol2는 name과 age가 리터럴 타입으로 고정됩니다.
let idol = { name: "이한", age: 22, }; // 타입은 { name: string, age: number }로 추론됨 const idol2 = { name: "이한", age: 22, }; // 타입은 { name: "이한", age: 22 }로 고정됨
- 타입 캐스팅은 변수나 값의 타입을 명시적으로 지정하는 방법입니다.
- as 키워드를 사용하여 값을 특정 타입으로 간주할 수 있습니다.
- 객체의 값이 변경되지 않도록 고정할 때 유용합니다.
const Leehan = { name: "이한" as const, // "이한" 리터럴 타입으로 고정 age: 22 as const, // 22 리터럴 타입으로 고정 };
- 배열에 포함된 값들의 타입을 기반으로 배열 전체의 타입을 추론합니다.
- const로 선언된 배열은 그 길이와 요소의 타입도 고정됩니다.
① 일반 배열 타입 추론
- numbers 배열은 숫자만 포함된 배열로 추론됩니다.
- numbersAndString 배열은 숫자와 문자열을 모두 포함할 수 있는 배열로 추론됩니다.
// 타입은 number[]로 추론됨 let numbers = [1, 2, 3, 4, 5]; // 타입은 (number | string)[]로 추론됨 let numbersAndString = [1, 2, 3, "4", "5"];
② 배열에 값 추가
- numbers 배열은 number[] 타입이므로 "6"과 같은 string을 추가할 수 없습니다.
- numbersAndString 배열은 (number | string)[] 타입이므로 추가할 수 있습니다.
// 오류: 'string' 타입은 'number[]' 배열에 추가할 수 없음 numbers.push("6"); // 정상: 배열 요소는 number와 string 타입을 모두 가질 수 있음 numbersAndString.push("6");
③ as const로 배열 고정
- twoNumbers 배열은 as const로 선언되어 값이 고정됩니다.
- 배열은 읽기 전용 배열이 되며, 값의 변경이나 추가가 불가능합니다.
- 배열의 길이와 요소가 고정되어 리터럴 타입으로 취급됩니다.
// 배열의 길이와 타입이 고정됨 const twoNumbers = [1, 3] as const; // 오류: 'push' 메서드는 읽기 전용 배열에서 사용할 수 없음 // twoNumbers.push(4); // first는 1로 고정됨 const first = twoNumbers[0];
1. 가독성 향상
- 변수에 값을 할당하면 자동으로 타입이 추론되므로, 코드가 간결하고 읽기 쉬워집니다.
- 명시적으로 타입을 지정하지 않아도 자동으로 처리합니다.
2. 타입 안정성
- 타입을 강제하여 런타임 오류를 방지하고, 타입 관련 문제를 미리 잡을 수 있게 돕습니다.
3. 유지보수 용이
- 타입을 추론하므로 코드 변경 시 다른 곳에 영향을 미치지 않도록 해줍니다.
- 타입 선언을 일일이 추가할 필요가 없어 유지보수가 쉬워집니다.
4. 개발 속도 향상
- 불필요한 타입 선언을 생략할 수 있어 코드 작성 속도가 빨라집니다.
1. 변수타입 추론
- userName 변수를 선언하고 "장원영"이라는 문자열을 할당하세요.
- userAge 변수를 선언하고 숫자 19를 할당하세요.
- userConstName 변수를 const로 선언하고 "안유진" 값을 할당하세요.
- userConstName을 "김채원"으로 변경하면 오류가 발생하는지 확인하세요.
let userName = "장원영"; let userAge = 19; const userConstName = "안유진"; // 오류 // const userConstName = "김채원";
2. 객체 속성 변경
- idol1 객체를 let으로 선언하고 name 속성에 "아이유", age 속성에 30을 할당하세요.
- idol1의 name 속성을 "수지"로 변경하세요.
- idol2 객체를 const로 선언하고 같은 데이터를 저장하세요.
- idol2의 name을 "제니"로 변경할 수 있는지 확인하세요.
let idol1 = { name: "아이유", age: 30, }; // name 속성 변경은 가능 idol1.name = "수지"; const idol2 = { name: "아이유", age: 30, }; // name 속성 변경은 가능 idol2.name = "제니"; // const로 선언된 객체는 재할당 불가 // idol2 = { name: "지수", age: 25 }; // 오류
3. 배열과 타입 제어
- 숫자로만 이루어진 배열 numbers를 선언하고 [10, 20, 30]을 할당하세요.
- numbers 배열에 40을 추가해보세요.
- numbers 배열에 "50"을 추가하려고 하면 어떤 오류가 발생하는지 확인하세요.
- 튜플 numbersTuple을 선언하고 [1, 2]로 설정하세요.
- as const를 사용해 수정할 수 없게 만드세요.
- numbersTuple.push(3);를 실행하면 어떤 오류가 발생하는지 확인하세요.
let numbers = [10, 20, 30]; numbers.push(40); // numbers.push("50"); let numbersTuple = [1, 2] as const; // numbersTuple.push(3);
36일차 후기
- 한 번도 들어보지 못한 부분을 수업해서.. 새로운거라? 좋았습니다.
- 오늘 수업 내용도 직접 사용해본 적은 없어서 그런지 뭐가 좋은지는 모르겠습니다.
- 요즘 취업 시장에서 타입스크립트는 기본이라고 하니 열심히 배워보겠습니다.
- Enum 발음을 들을 때마다.. 이놈!! 이라고 들려서 웃참을 했습니다.
- 오늘 수업도 모르는 부분 없이 다 이해하고 넘어간 것 같습니다. ✧₊⁎˓˓⁽̨̡ ˚͈́꒳˚͈̀*⁾̧̢˒˒⁎⁺˳✧༚
- 손에 익숙하지 않은 부분이라 실습을 계속 해봐야할 것 같습니다. (๑><๑)۶
enum을 사용하여 다크모드를 구현해보세요. 그럼 감이 오실거에요 ㅎ