[인프런 타입스크립트 입문 - 기초부터 실전까지] - 타입 단언 ~ 수업 마무리

Lee Jeong Min·2021년 12월 19일
0

TypeScript

목록 보기
8/18
post-thumbnail

이 글은 타입스크립트 입문 - 기초부터 실전까지의 타입단언 ~ 수업 마무리 부분을 보고 정리한 글입니다.

타입 단언

타입 단언 소개

// 타입 단언(type assertion)
var a;
a = 20;
a = 'a';
var b = a as string;

현재 a는 any타입인데 a에 숫자 20, 문자열 a같은 것들을 할당을 하면 개발자는 변수 a의 타입이 나중에 무엇이 될 것인지 알고 있다.
이러한 상황과 같이 타입스크립트보다 개발자가 타입을 더 잘알고 있는 경우, 직접 as 문법을 사용하여 타입을 단언해줌.

타입 단언의 실제 사례는 DOM API를 들어갈때 가장많이 사용!

타입 단언 예제

var div = document.querySelector('div');
div.innerText

// 타입 단언
var div = document.querySelector('div') as HTMLDivElement;
div.innerText

위와 같은 코드에서 ts는 div라는 변수에 HTMLDivElement 혹은 null값이 담길 수 있기 때문에, 이 타입이 무엇인지 한번 더 검증하는 과정을 필요로 한다.
이러한 경우 as HTMLDivElement와 같이 개발자가 타입 단언을 하게되면 div의 타입은 HTMLDivElement로 되고, 더이상 에러가 발생하지 않는 것을 확인할 수 있다.

이와 같이 개발자가 타입스크립트보다 이 타입에 대해 정확하게 알고 있는 경우, 타입 단언을 사용하여 타입을 명시해줄 수 있다.

타입 가드

타입 가드를 위한 예제 소개

interface Developer {
 name: string;
 skill: string;
}

interface Person {
 name: string;
 age: number;
}

function introduce(): Developer | Person {
    return { name: 'Tony', age: 33, skill: 'Iron Making'}
}
var tony = introduce();
console.log(tony.skill);

위의 코드에서 introduce 함수의 리턴 값은 DeveloperPersonUnion 값이다. 따라서 console.log(tony.skill) 부분에서 에러가 발생하는데 유니온 타입은 이 두가지 인터페이스의 공통된 속성인 name 만 가지고 있다고 판단하기 때문이다.

if ((tony as Developer).skill) {
    var skill = (tony as Developer).skill;
    console.log(skill);   
} else if((tony as Person).age) {
    var age = (tony as Person).age;
    console.log(age);  
}

다음과 같은 타입 단언을 이용한 코드로 skillage를 출력할 수 있다. 그러나 코드에서 볼 수 있듯이, 코드의 중복과 가독성 측면에서 좋지 않다. --> 이를 위해 타입 가드를 사용한다

타입 가드 소개와 적용

// 타입 가드 정의
function isDeveloper(target: Developer | Person): target is Developer {
    return (target as Developer).skill !== undefined;
}

if (isDeveloper(tony)) {
    tony.skill;
} else {
    tony.age
}

isDeveloper라는 타입 가드를 사용하여 targetDeveloper 일 때와, Person 일 때를 구분한 것을 확인할 수 있다. 이를 활용한다면 아까 전의 중복되는 코드들보다 더 깔끔하게 코드를 작성할 수 있고, if 조건문 안에서 타입스크립트가 타입 추론을 하여 메서드를 제공해주는 것을 확인할 수 있다.

타입 호환

타입 호환이란?

타입 호환이란 타입 스크립트에서 특정 타입이 다른 타입에 잘 맞는지를 의미한다.

interface Ironman {
  name: string;
}

class Avengers {
  name: string;
}

let i: Ironman;
i = new Avengers(); // OK, because of structural typing

코드의 구조 관점에서 타입이 서로 호환되는 것을 판단하기 때문에 에러가 발생하지 않는다.

참고 사이트: 타입호환

타입 호환 예제 - 인터페이스, 클래스

// 인터페이스
interface Developer {
    name: string;
    skill: string;
}

// interface Person {
//     name: string;
// }

class Person {
    name: string;
}

var developer: Developer;
var person: Person;
developer = person;
// person = developer // 에러 안남

developer라는 변수는 Developer를 인터페이스로 하기 때문에 nameskill속성이 필요한데, personname 속성만 가지고 있어 에러가 발생하게 된다. 이는 intefaceinterface뿐만아니라 interfaceclass간 끼리도 타입호환을 하며, 구조적 관점에서 타입 호환을 검사한다.

타입 호환 예제 - 함수, 제네릭

// 함수
var add = function(a: number) {
    
}

var sum = function(a: number, b: number) {

}

sum = add;
// add = sum;

인터페이스와 클래스와는 다르게 함수에서는 인수로 전달받는 타입의 개수가 많은 것이 좀 더 넓은범위(구조적으로 더 큼)이기 때문에 sum=add와 같은 할당은 되지만, add=sum과 같은 할당을 하게되면 에러가 발생한다.

// 제네릭
interface Empty<T> {

}
var empty1: Empty<string>;
var empty2: Empty<number>;
empty1 = empty2;
empty2 = empty1;

interface NotEmpty<T> {
    data: T;
}

var notempty1: NotEmpty<string>;
var notempty2: NotEmpty<number>;
notempty1 = notempty2; // 에러
notempty2 = notempty1; // 에러

제네릭에서 위의 Empty의 경우, 인터페이스 안 구조가 비어이씩 때문에 empty1, empty2 둘다 할당을 하여도 문제가 되지 않는다. 그러나 NotEmpty는 인수를 받아 data에 타입을 주기 때문에 notempty1 notempty2가 서로 할당을 하게 되면 구조적 타이핑에 의해 타입이 다르므로 에러가 발생한다.

타입 모듈화

타입스크립트의 모듈 시스템

ts-modules/app.ts

interface Todo {
    title: string;
    checked: boolean;
}

var item: Todo = {
    title: '할 일 1',
    checked: false,
}

처음에 개발을 할 때에 코드가 짧을 때에는 같은 공간에 인터페이스와 변수를 같이 정의하여 사용하다가, 후에 코드의 길이가 길어지게되면 유지보수성과 가독성을 위해 코드를 분리하게 된다.

ts-modules/types.ts

export interface Todo {
    title: string;
    checked: boolean;
}

ts-modules/app.ts

import { Todo } from './types'

var item: Todo = {
    title: '할 일 1',
    checked: false,
}

ES6+ Modules개념과 유사하게 다음과 같이 코드를 모듈화 할 수 있다.

자바스크립트의 모듈 시스템

이 부분에 대한 내용은 자바스크립트 모듈화와 관련된 내용이라 아래 자료를 참고하면 좋을 것 같다.

  • 모듈화의 필요성 (JS 기본적으로 유효범위가 전역이기 때문)
  • import & export 기본 문법
  • import & export 기본 예제
  • 브라우저 지원 범위 (웹팩 필요)

참고자료: 자바스크립트-모듈

전화번호부 애플리케이션에 모듈화 실습 & 풀이

깃헙 실습 코드

=> 타입스크립트 모듈화

수업 마무리

수업 정리 및 실전 프로젝트로 배우는 타입스크립트로 이어서 듣자

profile
It is possible for ordinary people to choose to be extraordinary.

0개의 댓글