바스키아
TypeScript) Intersection & Union Types 본문
Intersection 타입?? 영어가 약하므로 우선
횡단, 교차?
우선 예제로 보자
1
2
3
4
5
6
7
8
9
10
|
interface User {
name: string;
}
interface Action {
do() : void;
}
function createUserAction(u: User, a: Action) {
return { ...u, ...a};
}
|
우선 두 interface 를 합치는 함수가 있다고 하자.
그럼 저 리턴값에 대한 타입을 정의할때
interface Sum{
name:string;
do() : void
}
따로 인터페이스를 만들어서
function createUserAction(u: user, a: Action) : Sum{
return {...u, ...a}
}
이렇게 리턴타입을 정해줘야하는거니?? ---> 이럴때 intersection 을 쓰라는 것이다. & 엔드 쓰라고!!
1
2
3
4
5
6
7
8
9
10
|
interface User {
name: string;
}
interface Action {
do() : void;
}
function createUserAction(u: User, a: Action) : User & Action {
return { ...u, ...a};
}
|
요렇게.... ㅎㅎ ( 이러면 타입들을 모아놓은 interface 파일이 좀 줄어들겠네 ㅎㅎ)
그러면 이제 Union Types은 무엇인가....
합..친다??
이것도 예제를 봅시다. 만약 두값을 교하는 함수가 있다고 합시다.
1
2
3
|
function compare(x: string | number, y: string | number) {
}
|
파라미터 타입이 이상하다? ----> "|" 라는 or 연산자를 사용해서 x에 문자열 또는 number가 받아질수 있다는 것을 암시한다.
or 기호를 사용해서 표현하는 것이 union Types
x.를 확인하면 다음과 같은 파라미터 타입을 받는다는 설명이 뜬다
1
2
3
4
5
6
7
8
9
10
11
12
13
14
|
function compare(x: string | number, y: string | number) {
if(typeof x === 'number' && typeof y ==='number'){
return x === y ? 0 : x > y ? 1 : -1;
}
if(typeof x === 'string' && typeof y ==='string'){
return '위에와 같지뭐 ㅎㅎ';
}
throw Error('not supported type');
}
const v = compare(1,2);
const v = compare("a","b");
const v = compare("a",2);
|
typeof 로 파라미터 타입을 구분하여 함수식을 완성할수도 있다.
여까지 이해가 되었는가???
첫번째 if문은 x, y 파라미터가 각각 숫자타입으로 들어왔다면
x, y가 같을떄는 0 을 반환 , x가 크다면 1를 반환 y가 크다면 -1을 반환한다는 얘기다
위와같이 만든 campare함수에 (숫자, 문자열) 을 집어 넣으면 오류 메세지가 나올것이다.. 맞지?
이를 이용해서 임의의 값을 주었을 때 console.log로 정렬되어 찍어낼수도 있겠다.
1
2
3
4
5
6
7
8
9
10
11
12
|
function compare(x: string | number, y: string | number) {
if(typeof x === 'number' && && typeof y ==='number'){
return x === y ? 0 : x > y ? 1 : -1;
}
if(typeof x === 'string' && && typeof y ==='string'){
return x.localeCompare(y);
}
throw Error('not supported type');
}
console.log([3,2,1].sort(compare));
console.log(['c','a','b'].sort(compare));
|
콘솔을 찍어내면
여기서 stirng.localeCompare() 메서드는 기준 문자열과 비교했을 때 비교 대상 문자열이 정렬상 전에 오는지,
후에 오는지 혹은 같은 순서에 배치되는지를 알려주는 숫자를 리턴해준다.
console.log('a'.localeCompare('b')); // -1
console.log('b'.localeCompare('a')); // 1
console.log('b'.localeCompare('b')); // 0
(요기나게 쓸거같아서....ㅎㅎ)
이번엔 primitive 타입이 아닌 interface를 union type으로 적용했을때 보자
1
2
3
4
5
6
7
8
9
|
interface User {
name: string;
}
interface Action {
do() : void;
}
function process(v: User | Action) {
if(typeof v === "")
}
|
별다를거 없어 보인다....그런데??
알아둬야할것이 인터페이스는 자바스크립트에서 존재하지 않는다!!! 즉?
primitive 타입밖에...typeof는 자바스크립트 문법이잖아..!!! 그럼 object 써주면되는거 아니야?
--> 그럼 둘이 타입이 구분이 되지않아...멍청아.
그럼 이렇게하면 되지 않아??
-->
function process(v: User | Action) {
if (v.do) 이렇게 말이다....
}
User | Action 은 유니온 타입이기때문에( 합쳐 졌기때문에 ) v.do는 혼란이 온다. 그럴땐 이와같이 해결하는 방법이있다.
1
2
3
|
function process(v: User | Action) {
if ((<Action>v).do) {
(<Action>v).do()
}
}
|
이렇게 타입을 구별 할수 있다. 근데 좀 지저분한데?? 매번 타입을 이렇게 지정하면....좀그래
---> 직접 타입가드를 만들어보자
1
2
3
4
5
6
7
8
9
10
|
function isAction(v: User | Action): v is Action {
return (<Acton>v).do) !== undefined;
}
function process(v: User | Action) {
if (isAction(v)) {
v.do()
} else {
console.log(v.name)
}
|
실제 프로젝트에서 이렇게까지 쓰일진 모르겠지만 틈이보이면 바로 적용해봐야 겠다.
'JS > TypeScript' 카테고리의 다른 글
TypeScript) tsconfig.ts 설정하기 (0) | 2019.08.31 |
---|---|
TypeScript 클래스 (Class Type) (0) | 2019.08.29 |
TypeScript Enum (0) | 2019.08.29 |
TypeScript 함수형 타입(function Type) (0) | 2019.08.29 |
TypeScript 인터페이스(Interface) (0) | 2019.08.29 |