Typescript 구조적 타이핑

승훈·2022년 9월 28일
0

타입시스템은 '구조적으로 타입이 맞기만 하다면 이를 허용.. 이를 구조적 타이핑
다른 java, c# 같은 언어에서는 허용하지 않음

이는 javascript 코드의 일반적인 작성 방식에 따라 설계되었다.
js는 함수 표현식, 객체 리터럴 같은 익명 객체를 사용하기 떄문에 관계의 타입을 명목적인 타입 시스템보다
구조적 타입 시스템을 이용하여 표현하는것이 더욱 자연스럽다.

자바스크립트는 덕타이핑 특성을 가지고 있고, 타입스크립트는 구조적 타이핑을 활용하여 이 모델을 구현해 냈다고 볼 수 있다.
인터페이스에 할당 되는 값은, 형식적으로 선언되어 있는 속성 이상의 속성을 추가로 가질 수 있다. 즉 열려 있다.

  • 클래스 또한 구조적 타이핑을 따르고 있으므로 조심해야 한다.
interface CompareNumber {
  x: number
  y: number
}

function calc(v: Vector2D) {
  return v.x > v.y
}

interface CompareNumberName extends CompareNumber {
  name: string
}

const a: CompareNumberName = { name: 'c1', x: 5, y: 10 }
calc(a) // works fine ... 개발자가 원하지 않는 상황이지만 에러가 발생하지 않음..
물론 js에서도 문자(ascii)를 서로 비교 할 수 있음. 하지만 필자가 적은 calc 함수는 그런 용도가 아님
  • 구조적 타이핑은 유닛 테스트 시에 유용하다.... 예를 들어 db qurey 요청 함수를 테스트 할때
    db를 mocking 할 필요 없이 DB를 추상화하여 안전하게 동작시킬 수 있다.
interface Employee {
  name: string
  id: number
}

interface DB {
  runQuery: (sql: string) => any[]
}

function getEmployee(db: DB): Employee[] {
  const rows = db.runQuery('SELECT name, id from EMPLOYEES')
  return rows.map((row) => ({ name: row[0], id: row[1] }))
}

결론적으로 typescript를 사용하는 한 타입 정의에 대한 컴파일 장점도 있지만 이렇게 원치 않는 상황으로 버그가 발생할 수 있다..

0개의 댓글