타입스크립트 TS 공부 #6 Intersection type, Union type, Index type, 타입 별칭

사공 오·2022년 5월 5일
0

TS 기초 공부

목록 보기
6/7
post-thumbnail

Intersection type

여러타입이 하나로 합쳐진 타입

interface User {
    name: String;
}

interface Action {
    do(): void;
}

function createUserAction(u: User, a: Action): User & Action { //&를 사용해서 인터섹션(교집합)타입을 만드는 방법
    return { ...u, ...a};
}

const u = createUserAction({name: 'ony'}, { do() {} }); // 기존타입을 활용해서 위의 두타입을 같이 합쳐져야할떄 사용

Union type

| 를 사용해서 만드는 유니언(합집합)타입


function compare(x: string, y: string)
function compare(x: number, y: number)
function compare(x: string | number, y: string | number) { // ||를 사용해서 유니언(합집합)타입을 만드는 방법을 배움
   // x. //x. 하면 string과 number 두가지타입에서 모두 사용가능한 매서드만 나온다

   // 유니언 타입에서는 같은 타입끼리 비교하고 싶다면 타입가드 만들기 
   if(typeof x === typeof 'number' && typeof y === 'number'){
       return x === y ? 0 : x> y ? 1 : -1;
       // 두개가 같으면 0 아니면 x>y이면 1반환 아니면 -1반환
   }
   if(typeof x === typeof 'string' && typeof y === 'string'){
       return x.localeCompare(y);
   }
   throw Error('not supported type');
}

const v1 = compare(1,2);
const v2 = compare("a","b");
// const v3 = compare("a",1); - 이렇게 하면 오류발생 위에 펑션 넣는 값을 적어줘서

console.log([3,2,1].sort(compare)) //소팅할때 컴페어 전달할 수 있음  - 앞에 안에 넣을 값을  숫자 넣어서 코드가 동작됨
console.log(['c','b','a'].sort(compare)) //소팅할떄 컴페어 전달할 수 있음  - 앞에 안에 넣을 값을  문자열 넣어서 코드가 동작됨

tsc 
node dist/intersection-union.js

터미널에 위에 두줄을 입력하면 [1,2,3] 하고 ['a','b','c']가 출력됨


타입가드가 아닌 바로 type assertion을 처리해서 원하는 타입으로 고정하기


function isAction(v: User | Action) : v is Action {
    return (<Action>v).do !== undefined; //Action>v가 do라는 속성이 있으면 얘는 액션이라고 본다
} //타입가드가 아니고 바로 type assertion을 처리해서 원하는 타입으로 고정해서 하단의 코드를 쓸수도 있음 

function process(v: User | Action){ //매서드를 가져야하는 타입인데 인터페이스는 자바스크립트에 존재하지않음
    //if (typeof v === "object") - 오브젝트 인지못해서 하면안된다
    
    //if ((<Action>v).do) {//v가 Action이라고 생각하고 이 코드를 작성한다고 말해서 type assertion  (<Action>v).do .do라는 매서드에 접근가능
    //(<Action>v).do} // 이렇게 매번 해야하는데 이거를 안하려면
    
    if(isAction(v)){
        v.do();
    } else {
        console.log(v.name);
    }
}



Index Type

속성의 이름이 정해져있지않고 동적으로 처리해야할때 사용

interface Props {
    name: string;
    [key: string]: string; //key: 의 값은 string과 number만 가능
}

const p: Props = {
    name: 'hello',

    a: 'd',
    b: 'e',
    c: '3',
   // d: 3, //문자가 아니라서 오류남
   0: 'ㅇ',
   1: 'b'
}
p.name // 접근가능
p.dfsf // 인덱스 타입이라서 이떠한 뮨자열값도 접근이 된대 - 어떠한 키값이 나오는지 모를때 쓸 수 있다.?

p['a'] // 이렇게 키이름으로 접근가능
p[0] // 이렇게 숫자로도 접근가능 - 값은 'ㅇ'

keyof 연산자

유저의 특정타입의 키들(키의 이름이나 그것의 타입)에 접근함

let keys: keyof Props;

interface User3 {
    name: string; 
    age: number;
    hello(msg: string): void;
}

let keysOfUser: keyof User3; // 변수에 User3 의 키의 이름들(name, age,hello)이 유니언형태로 보이게 됨 
keysOfUser ='age'

let helloMethod: User3["hello"]; // 이 변수는 User3의 "hello"타입만 할당할 수 있다
helloMethod = function(msg: string){ //스트링말고 넘버로 정의하면 오류남 헬로랑 타입이 같아야함

}

타입별칭

인터페이스와 비슷하지만 타입에 별칭을 지정할 수 있다

 interface User {
    name: String;
}

interface Action {
    do(): void;
}

type UserAction = User & Action;
function createUserAction(): UserAction { // 리턴값이 UserAction
    return {
        do() {},
        name: ''
    }
}

//---


type UserState = "PENDING" | "APPROVED" | "REJECTED";

function checkUser(user: User2): UserState { //유저 검사 결과가 타입 유저상태로 나오게한다
    if(user.login()) {
        return "APPROVED";
    } else {
        return "REJECTED";
    }
}
  • 함수의 리턴값을 타입 별칭으로 정의한 타입으로 고정 가능

type StringOrNumber = string | number; // 원시형 타입도 사용가능

type Arr<T> = T[]; //제네릭도 타입별칭 사용가능 - T에 해당하는 배열의 타입별칭이 Arr
type P<T> = Promise<T>; // 프로미스(이전에 있던 타입)를 축약시켜서 이름(별칭)을 부여할수있음
  • 원시형타입, 제네릭, 프로미스와같은 이전에 있던 타입도 축약시켜 이름(별칭)을 부여할수있음
type User2 = {
    name: string;
    login(): boolean;
}

class UserImpl implements User2 { //인터페이스가 아닌데도 implements가 가능함
    login(): boolean {
        throw new Error("Method not implemented.");
    } 
    name: string;
}
  • 인터페이스가 아니어도 implements가 가능함

0개의 댓글