[TypeScript] 이펙티브 타입스크립트 (item 03 ~ 05)
TypeScript

[TypeScript] 이펙티브 타입스크립트 (item 03 ~ 05)

반응형

item 03. 코드 생성과 타입은 관계가 없다.

  • 최신 타입/자바스크립트를 브라우저에서 동작할 수 있도록 구버전의 자바스크립트로 트랜스파일(transpile)합니다.
  • 코드의 타입 오류체크합니다.

그러나 두가지는 서로 완벽히 독립적 입니다. 그렇기 때문에 타입체크는 컴파일에 영향을 미치지 않습니다.
즉 타입체크에서 오류가 발생해도 컴파일이 됩니다.

// test.ts
let x = "hello";
x = 1234;
// ~ number 형식은 string에 할당될 수 업습니다.

// tsc test.ts ->

// test.js
let x = "hello";
x = 1234;
  • interface 등의 타입은 컴파일 과정중에 제거되기 때문에 런타임 시점에서는 아무 역활을 하지 않습니다.
interface Car {
  name: string;
}

interface Truck extends Car {
  weight: number;
}

type Vehicle = Car | Truck;

function foo(ele: Vehicle) {
  if (ele instanceof Truck) {
    return ele.weight;
  } else {
    return ele.weight;
  }
}

// instanceof는 결국 ele 가 Truck이라는 생성자에 해당 값이 존재하는지를 판별하는 것인데
// Truck은 오로지 type의 역활만을 하고 type은 런타임환경에서는 제거된 상태이다.

// 그렇기 때문에 런타임환경에서는 아무역활을 하지 못한다.

item 04. 구조적 타이핑에 익숙해지기

자바스크립트는 기보적으로 덕 타이핑 기반이다. (객체가 어떤 타입에 부합하는 변수와 메서드를 가질 경우 객체를 해당 타입에 속하는것으로 간주하는 방식 오리와 같은 특성을 지닌다면 오리가 아니더라도 오리인것으로 간주한다.)

  • 자바스크립트가 덕 타이핑 기반이고 타입스크립트가 이를 모델링하기위해 구조적 타이핑을 사용함을 이해한다.
interface A {
  x: number;
  y: number;
}

interface B {
  x: number;
  y: number;
  z: number;
}

function foo(v: A) {
  return v.x + v.y;
}

const a: A = { x: 3, y: 3 };
const b: B = { x: 3, y: 3, z: 4 };
foo(a);
foo(b);

// foo 함수는 x, y 만을 가지는 type A 여야 하는데 x, y, z 를 가지는 type B를 넣더라도 에러를 발생시키지 않는다.
// 즉 TypeScript는 A의 속성 x, y 가 B에 모두 존재하기 때문에 A가 B에 속한다(호환이 된다)고 판단을 한다.
// 그래서 a 의 상위인 b를 넣어도 에러를 발생시키지 않는 것이다.
  • 타입이 열려있다. 봉인되어있지 않다는 것은 추가적인 속성들이 들어와도 error가 발생하지 않는다는 것이다.
interface A {
  x: number;
  y: number;
}

interface B {
  x: number;
  y: number;
  z: number;
}

function foo(v: A) {
  let result = 0;

  for (const key of Object.keys(v)) {
    const value = v[key];
    result += value;
  }
  return result;
}

const a: A = { x: 3, y: 3 };
const b: B = { x: 3, y: 3, z: 3 };
const c = { x: 3, y: 3, z: 4, k: "string" };

console.log(foo(a));
console.log(foo(b));
console.log(foo(c));

// foo함수는 A라는 객체의 type인데 매개변수로 A 객체가 아닌 다른 객체를 넣어주어도 A의 속성(x, y)를 가지고 있고
// 추가적으로 z 를 가진 B type의 객체와 z, k 를 가진 타입을 지정해주지않은 객체를 매개변수로 넣어주더라도 error를 발생시키지 않는다.

// 이런것이 type은 열려있는 상태(open)라는 것 같다.

item 05. any 타입 사용을 지향해야 하는 이유

  • any 타입을 사용하면 타입체커와 타입스크립트 언어서비스를 무력화 시킵니다.
// 1. 타입체커 무력화
function calculateAge(birthDate: Date): number {
  return 0;
}

let birthDate: any = "1995-12-22";

calculateArea(birthDate); // OK 가 되면 안된다. why? birthDate는 Date 타입이 아니기 때문에


// 2.언어서비스를 적용 x (자동완성 기능?, 이름 변경 기능)
let person: any = { first: 'Ahn' };
person.first
person. // 자동완성 기능이 동작하지 않는다.
  • any 타입은 진짜 문제점을 감추고, 개발경험을 나쁘게하고, 타입시스템의 신뢰도를 떨어뜨린다.
반응형

'TypeScript' 카테고리의 다른 글

[TypeScript] 이펙티브 타입스크립트 (item 01 ~ 02)  (0) 2022.01.26