React : TypeScript 심화 개념과 코드 설명

민의균·2024년 8월 23일
0

React

목록 보기
4/13
post-thumbnail

이 글은 TypeScript의 기초 개념을 다룬 이전 포스팅에 이어, TypeScript의 심화 개념들을 설명하고자 합니다. 특히, 인터페이스 병합, 제네릭, 타입 가드 등 중요한 TypeScript 기능들을 이해하고 실습할 수 있도록 구성했습니다. 이 내용을 통해 TypeScript의 심화 개념을 쉽게 이해하고 실전에서 활용할 수 있기를 바랍니다.


1. 인터페이스 병합

설명: TypeScript에서는 동일한 이름의 인터페이스가 여러 번 선언되면, 이를 자동으로 병합합니다. 이를 통해 인터페이스를 확장하거나 필요한 속성을 추가할 수 있습니다.

interface IUser {
    name: string;
    age: number;
}

interface IUser {
    email: string;
}

const auser: IUser = {
    name: "John",
    age: 20,
    email: "John@gmail.com",
};

이 코드에서 두 번 선언된 IUser 인터페이스가 병합되어 name, age, email 모두를 포함하게 됩니다. 이를 통해 코드의 확장성을 자연스럽게 확보할 수 있습니다.

2. 함수 타입 인터페이스

인터페이스를 사용해 함수의 타입을 정의할 수 있습니다. 이를 통해 함수의 매개변수와 반환값의 타입을 명확히 할 수 있습니다.

interface IAdd {
    (n1: number, n2: number): number;
}

const aDd: IAdd = (n1, n2) => n1 + n2;

이러한 방식으로 함수의 구조를 명확히 정의하면, 코드의 일관성을 유지할 수 있고, 타입 안전성도 보장됩니다.

3. 인덱스 시그니처

인덱스 시그니처를 사용하면 객체의 키와 값의 타입을 정의할 수 있습니다. 이 기능은 동적으로 속성이 추가될 수 있는 객체에 유용합니다.

interface ICar {
    [key: string]: string | number;
}

const car: ICar = {
    name: "Benz",
    color: "black",
    price: 1000,
};

이 코드에서는 ICar 인터페이스가 키를 문자열로 받고, 값은 문자열이나 숫자일 수 있도록 정의됩니다.

4. 타입 추론

TypeScript는 초기값을 기준으로 변수의 타입을 자동으로 추론합니다. 이를 통해 타입을 명시하지 않아도 안전하게 코드를 작성할 수 있습니다.

let numd = 10;
numd = 20; // number로 자동 추론

let str = "A";
str = "B"; // string으로 자동 추론

타입 추론은 코드의 가독성을 높여주고, 불필요한 타입 선언을 줄여줍니다.

5. 타입 별칭 (Type Alias)

type 키워드를 사용해 타입을 별칭으로 정의할 수 있습니다. 이는 인터페이스와 유사하지만, 더 복잡한 타입이나 유니언 타입 등을 정의할 때 유용합니다.

type TUser = {
    name: string;
    age: number;
};

type Tjob = { job: string };
type TUserAndJob = TUser & Tjob; // 타입 병합

const user2: TUser = {
    name: "Neo",
    age: 85,
};

타입 별칭은 코드의 재사용성을 높이고, 복잡한 타입 구조를 간결하게 표현할 수 있습니다.

6. 열거형 (Enum)

enum은 관련된 상수들의 집합을 정의하는 데 사용됩니다. 숫자형과 문자형 열거형을 모두 지원하며, 명확한 값의 집합을 표현할 때 유용합니다.

enum Role {
    Admin = "admin",
    User = "user",
    Guest = "guest",
}

const user: IUser = {
    name: "Neo",
    role: Role.User,
};

열거형을 사용하면 상수를 코드에서 직접 사용하는 대신 의미 있는 이름으로 관리할 수 있어 코드의 가독성이 향상됩니다.

7. 제네릭 (Generics)

제네릭은 다양한 타입에 대해 동작할 수 있는 함수를 작성할 수 있게 해줍니다. 이를 통해 코드의 재사용성을 극대화할 수 있습니다.

function getSize<T>(arr: T[]): number {
    return arr.length;
}

console.log(getSize<number>([1, 2, 3])); // 3
console.log(getSize<string>(["a", "b", "c"])); // 3

제네릭은 함수나 클래스에서 다양한 타입을 유연하게 다룰 수 있게 해주며, 코드의 재사용성을 높여줍니다.

8. 타입 가드 (Type Guard)

타입 가드는 변수의 타입을 좁혀 특정 타입에 대해 안전하게 작업할 수 있게 합니다.

const getRetunValue = (n: number | string) => {
    if (typeof n === "number") return n.toFixed(1);
    else return n;
};

타입 가드를 사용하면 복합 타입에서 안전하게 작업할 수 있어 런타임 오류를 줄일 수 있습니다.

9. Todo 리스트 예제

이 예제는 TypeScript의 다양한 개념을 종합적으로 활용한 예제입니다. 인터페이스로 Todo 아이템의 구조를 정의하고, CRUD 작업을 수행합니다.

interface Todo {
    id: number;
    text: string;
    completed: boolean;
}

const todos: Todo[] = [];

const addTodo = (text: string): void => {
    const todo: Todo = {
        id: todos.length + 1,
        text,
        completed: false,
    };
    todos.push(todo);
};

const removeTodo = (id: number): void => {
    const findIndex = todos.findIndex((todo) => todo.id === id);
    if (findIndex !== -1) {
        todos.splice(findIndex, 1);
    }
};

const toggleTodo = (id: number): void => {
    const find = todos.find((todo) => todo.id === id);
    if (find) {
        find.completed = !find.completed;
    }
};

이 Todo 리스트 예제에서는 TypeScript의 다양한 기능을 실전에서 어떻게 활용할 수 있는지 배울 수 있습니다. 인터페이스를 통해 객체의 구조를 명확히 하고, 제네릭과 타입 가드 등을 통해 코드의 안정성과 재사용성을 극대화할 수 있었습니다.



참말로 어질어질하죠잉?


이번 글에서는 TypeScript의 심화 개념을 다루었습니다. 인터페이스 병합, 제네릭, 타입 가드 등 TypeScript의 강력한 기능을 통해 코드의 안정성과 재사용성을 크게 높일 수 있었습니다. TypeScript는 복잡한 애플리케이션에서도 타입 안전성을 보장하면서 효율적인 코드를 작성할 수 있게 해주는 매우 유용한 도구입니다. 이 글을 통해 TypeScript의 심화 개념을 이해하고, 실전 프로젝트에 적용해보시길 바랍니다.

profile
코린이

0개의 댓글