타입스크립트의 타입은 일반적으로 변경되지 않는다. 그러므로 객체를 생성할 때에 속성을 하나씩 추가하기보다는 여러 속성을 포함해서 한꺼번에 생성해야 타입 추론에 유리하다.
앞에서 봤듯이 타입스크립트에서는 객체의 타입을 체크할 때 해당 속성이 존재하는지 확인을 하기 때문에 존재하지 않는 속성을 추가할 수 없다. 그러므로 객체를 반드시 제각각 나눠서 만들어야 한다면 타입 단언문을 사용해 타입 체커를 통과하게 할 수 있다.
interface Point { x: number; y: number; }
const pt = {} as Point
pt.x = 3
pt.y = 4
작은 객체들을 조합해 큰 객체를 만들어야 하는 경우에도 여러 단계를 거치는 것은 좋지 않다.
const pt = { x: 3, y: 4 }
const id = { name: 'Yeseul' }
const namedPoint = {}
Object.assign(namedPoint, pt, id);
namedPoint.name; // ❗️'{}' 형식에 'name' 속성이 없습니다.
이럴 때는 객체 전개 연산자를 사용하면 큰 객체를 한꺼번에 만들어 낼 수 있다.
const namedPoint = {...pt, ...id};
namedPoint.name; // 정상, 타입이 string
객체 전개 연산자를 사용하면 타입 걱정 없이 필드 단위로 객체를 생성할 수도 있다.
const borough = { name: 'Brooklyn', location : [40.688, -73.979] }
const loc = borough.location
위 코드에서는 borough.location
에 loc
이라는 별칭(alias)을 만들었다. 별칭의 값을 변경하면 원래 속성값에도 반영된다.
이러한 별칭을 남발하게 되면 제어 흐름을 분석하기 어렵다.
const doSomething = (b: number) => {}
type Point = {x: number; y: number; z?: number}
const point = {x: 1, y: 2}
function doSomethingWihtPoint(point: Point) {
const pointZ = point.z
if(point.z) {
doSomething(pointX) // ❗️type is number | undefined
doSomething(point.z) // type is number
}
}
<이펙티브 타입스크립트> Dan Vanderkam, 프로그래밍 인사이트 (2021)