검색
검색
공개 노트 검색
회원가입로그인
TypeScript 정복하기: 초심자에서 전문가로

4장: 타입스크립트의 함수 – 매개변수와 반환 타입, 제네릭

함수의 진화: TypeScript에서 매개변수와 반환 타입 이해하기

코드를 구성하는 핵심 요소 중 하나가 함수입니다. TypeScript는 자바스크립트와 달리, 함수의 매개변수와 반환값에 타입을 명확히 지정할 수 있습니다. 이 변화는 코드의 안정성뿐 아니라, 개발자 자신과 동료 모두에게 큰 신뢰를 제공합니다.

함수를 정의할 때, 매개변수 옆에 콜론(:)과 타입을 붙이면 어떤 값만 허용되는지 명확히 알릴 수 있습니다. 예를 들어, 두 숫자를 더하는 함수를 만든다면 다음과 같습니다.

function add(a: number, b: number): number {
  return a + b;
}

이처럼 함수의 매개변수와 반환 타입 모두를 명시하면, 잘못된 값이 전달될 경우 컴파일 단계에서 오류가 발생합니다. 타입스크립트는 똑똑하여, 명확하게 타입을 표기하지 않아도 반환값이나 전달된 인자를 분석해 추론하지만, 복잡한 함수나 여러 사람이 협업할 때는 타입 표기가 명확할수록 유리합니다.

일관성과 안전성을 높이는 함수의 타입 선언

실제 프로젝트에서는 함수가 단순하지 않습니다. 매개변수의 개수가 달라질 수 있고, 반환값이 복잡할 수도 있습니다. 함수를 변수에 할당하거나 인수로 전달해야 하는 상황에서 "함수 타입" 선언이 빛을 발합니다.

let greet: (name: string) => string;
greet = function(name) {
  return `안녕하세요, ${name}`;
};

이 구조는 함수의 형태를 타입으로 명확히 정의해 주므로, 올바른 사용을 강제합니다.

선택적 매개변수와 기본값

인자가 항상 모두 필요하지 않을 때, 타입스크립트는 물음표(?) 표기로 "선택적 매개변수"를 지원합니다. 또한 매개변수에 기본값을 지정할 수 있어 사용의 유연성이 더욱 높아집니다.

function log(message: string, importance?: string): void {
  console.log(message, importance);
}

Generic 함수: 다양한 타입을 하나의 로직으로

복잡한 시스템에서는 입력값이 고정된 한 가지 타입일 수 없습니다. 이럴 때 타입스크립트가 제공하는 제네릭(Generic) 기능이 위력을 발휘합니다. 제네릭은 함수에 "타입을 인수로 전달"하여, 다양한 타입에도 동작하도록 만듭니다.

예를 들어, 전달받은 값을 그대로 반환하는 간단한 함수를 만들어보겠습니다.

function identity<T>(arg: T): T {
  return arg;
}

여기서 T는 타입의 자리표시자입니다. 함수 호출 시 타입을 명시할 수도 있고, 타입스크립트가 자동으로 추론하기도 합니다.

let output1 = identity<string>('Hello!');
let output2 = identity<number>(123);

이처럼 제네릭 함수를 이용하면, 같은 로직을 여러 타입에 적용하면서 타입 안전성을 잃지 않을 수 있습니다.

인자의 타입에 따라 달라지는 반환 타입

고급 사용 패턴으로, 함수의 매개변수 타입에 따라 반환 타입이 달라지는 형태도 가능합니다. 조건부 타입과 제네릭을 함께 활용하면 매우 유연한 API를 만들 수 있습니다. 예를 들어, 두 종류의 데이터 중 하나를 받아서 그에 맞는 타입을 반환하는 함수를 생각해볼 수 있습니다.

type Circle = { type: 'circle'; radius: number };
type Square = { type: 'square'; length: number };

function getShapeArea<T extends Circle | Square>(shape: T): T extends Circle ? number : string {
  if (shape.type === 'circle') {
    // @ts-expect-error: 타입 지정 예시용
    return Math.PI * shape.radius * shape.radius;
  } else {
    // @ts-expect-error: 타입 지정 예시용
    return `정사각형 넓이: ${shape.length * shape.length}`;
  }
}

이 기법은 스스로 타입을 정의하고, 함수의 동작 결과가 입력과 밀접히 연관될 때 매우 유용합니다.

정리

TypeScript의 함수는 단순히 로직을 재활용하는 수단이 아니라, 타입 시스템과 결합하여 버그를 예방하고, 협업 효율을 높이며, 코드의 신뢰도를 비약적으로 끌어올리는 도구입니다. 함수 타입, 선택적 매개변수, 제네릭, 조건부 타입 등 다양한 전략을 유연하게 활용하면 초심자에서 전문가로의 도약이 그리 먼 일이 아닙니다.


공유하기
카카오로 공유하기
페이스북 공유하기
트위터로 공유하기
url 복사하기