[Effective TypeScript] any 다루기(1)

이예슬·2022년 12월 11일
0

Effective TypeScript

목록 보기
13/15

타입스크립트의 타입 시스템은 선택적(optinal)이고 점진적(gradual)이기 때문에 정적이면서도 동적인 특정을 동시에 가진다. 따라서 타입스크립트는 프로그램의 일부분에만 타입 시스템을 적용할 수 있다. 이러한 특성으로 인해 점진적인 마이그레이션이 가능하다.

any는 타입스크립트에서 타입 체크를 비활성화시켜주는 타입이다. 현명하게 사용하면 타입스크립트 코드를 효과적으로 작성하는데 도움을 주지만 남용하게 되면 타입스크립트가 가진 장점을 사용할 수 없게 된다. 따라서 any에 대해 다루는 방법을 잘 익혀야 한다.

Item38. any 타입은 가능한 한 좁은 범위에서만 사용하기

function processBar(b: Bar) { ... } 

function f1() {
	const x : any = expresionReturningFoo()
	processBar(x) 
} 

function f2() {
	const x = expresionReturningFoo()
	processBar(x as any) 
} 

progressBar() 함수를 사용하기 위해 f1(), f2() 의 두 가지 방법을 사용할 수 있지만 두 가지 방법 중 f2() 가 더 좋은 방법이다. any 타입이 processBar 함수의 매개변수에서만 사용된 표현식이므로 다른 코드에는 영향을 미치지 않기 때문이다. f1() 함수를 사용한다면 이후에 x가 반환되더라도 타입 체크를 하지 않기 때문에 any가 코드 전체에 영향을 끼칠 수 있다.

타입스크립트가 함수의 반환 타입을 추론할 수 있는 경우에도 함수의 반환 타입을 명시하는 것이 좋다. 함수의 반환 타입을 명시하면 any 타입이 함수 바깥으로 영향을 미치는 것을 방지할 수 있기 때문이다.

이는 객체를 선언할 때에도 마찬가지이다.

const config: Config = {
	a: 1, 
	b: 2, 
	c: { key: value } as any
} 

const config: Config = {
	a: 1, 
	b: 2, 
	c: { key: value as any} 
} 

any 타입은 최소한의 범위에서만 사용하는 것이 좋다.

  • 강제로 타입 오류를 제거하려면 any 대신 @ts-ignore 를 사용하는 것이 좋다.

Item39. any를 구체적으로 변형해서 사용하기

any 타입은 매우 넓은 타입이다.

function getLengthBad(arr: any){
	return arr.length;
} 

function getLength(arr: any[]){
	return arr.length
}  

getLengthBad보다는 getLength를 사용하는 것이 더 좋은 이유는 아래와 같다.

  • 함수 내의 arr.length 타입이 체크된다.
  • 함수의 반환 타입이 any 대신 number로 추론된다.
  • 함수가 호출될 때 매개변수가 배열인지 체크된다.

함수의 타입에도 단순히 any를 사용하는 것은 좋지 않다. 최소한으로나마 구체화할 수 있는 방법을 사용해야 한다.

type FN0 = () => any; // 매개변수 없이 호출 가능한 모든 함수 
type FN1 = (arg: any) => any; // 매개변수 1개 
type FN2 = (...args: any[]) => any;  // 'Function' 타입과 동일

Item40. 함수 안으로 타입 단언문 감추기

함수의 모든 부분을 안전한 타입으로 구현하는 것이 이상적이지만 불필요한 예외 상황까지 고려해 가며 타입 정보를 힘들게 구성할 필요는 없다. 함수 내부에는 타입 단언을 사용하고 함수 외부로 드러나는 타입 정의를 정확히 명시하는 정도로 끝내는 게 낫다. 제대로 타입이 정의된 함수 안으로 타입 단언문을 감추는 것이 더 좋은 설계이다.


<이펙티브 타입스크립트> Dan Vanderkam, 프로그래밍 인사이트 (2021)

profile
꾸준히 열심히!

0개의 댓글