여러가지 타입을 갖는 프로퍼티를 갖는 새로운 타입 정의
일반적으로 타입 체크를 위해 사용되며 변수, 함수, 클래스에 사용가능
모든 메서드는 '추상 메서드' (단, abstract 키워드를 사용하지 않음)
interface User {
[grade: number]: 'A' | 'B' | 'C' | 'D';
}
let user: User = {
1: 'A',
4: 'D'
}
협업하여 개발시 공통적으로 사용되는 부분에 대해 미리 정의를 함
추후 코드를 합칠 때 효율적
?가 붙는 경우는 반드시 정의할 필요 없다.
interface User {
userName: string;
age?: number;
address?: string;
}
let user: User = {
userName: 'ddoni'
}
readonly가 붙는 경우는 처음 정의한 후 변경이 불가능하다.
interface를 확장할 때 extends 예약어를 사용한다.
interface Person {
name: string;
age?: number;
}
interface Developer extends Person {
type: 'frontEnd' | 'backEnd';
}
const developer: Developer = {
name: 'ddoni', // 상속한 프로퍼티를 꼭 정의
type: 'frontEnd'
}
클래스에서도 interface를 상속할 수 있으며 이 경우에는 impelements 예약어를 사용해야 한다.
콤마(,)를 사용하여 다중 인터페이스 확장이 가능하다.
interface Car {
color: string;
wheels: number;
start(): void;
}
interface Toy {
name: string;
}
interface ToyCar extends Car, Toy {
price: number;
}
let myCar: ToyCar = {
color: 'red',
wheels: 3,
start: () => {
console.log('start');
},
name: 'ddoni',
price: 10000
}
인터페이스는 함수 타입도 정의해줄 수 있다.
interface SquareFunc {
(num: number): number;
}
const squareFunc: SquareFunc = function(num: number): number {
return num*num;
}
인터페이스를 구현했다고해서 타입 체크를 통과하는 유일한 방법이 아님
타입 체크에서 중요한 것은 값을 실제 가지고 있느냐
interface IDuck {
quack(): void
}
class MallardDuck implements IDuck {
quack() {
console.log('Quack!');
}
}
class RedheadDuck {
quack() {
console.log('q~uack!');
}
}
function makeNoise(duck: IDuck):void {
duck.quack();
}
makeNoise(new MallardDuck());
makeNoise(new RedheadDuck()); // 오류가 나지 않는다.
interface IPerson {
name: string
}
function sayHello(person: IPerson): void {
console.log(`hello ${person.name}`);
}
const me = { name: 'Lee', age: 18 };
sayHello(me); // 변수 me에는 name이라는 값이 있기 때문에 패스가 된 것
sayHello({ name: 'error', age: 19 }); // 이거는 또 오류..
타입을 지정하여 선언하기 어려운 경우에 사용하며 선언 시점이 아니라 생성 시점에 타입을 명시하여 하나의 타입만이 아닌 다양한 타입을 사용할 수 있다.
재사용성이 높은 함수와 클래스를 생성할 수 있다.
오류를 쉽게 포착할 수 있다. ( any타입은 컴파일 시 타입을 체크하지 않는다 )
class Stack {
private data: any[] = [];
constructor() {}
push(item: any): void {
this.data.push(item);
}
pop(): any {
return this.data.pop();
}
}
const myStack = new Stack();
myStack.push(1);
myStack.push('a');
myStack.pop().substring(0);
myStack.pop().substring(0); // 오류 발생
위와 같은 경우 타입에 따라 새로운 클래스를 생성할수도 있지만 여러가지 타입이 필요한 경우 일일이 생성하기는 어렵기 때문에 이럴 때 Generic을 사용하면 유용하다.
class Stack<T> {
private data: T[] = [];
constructor() {}
push(item: T): void {
this.data.push(item);
}
pop(): T | undefined {
return this.data.pop();
}
}
const myStack1 = new Stack<number>(); // number 타입만
const myStack2 = new Stack<string>(); // string 타입만
function toPair<T, U>(a: T, b: U): [T, U] {
return [a, b];
}
toPair<string, string>('1', '2');
toPair<string, number>('1', 2);
interface Mobile<T> {
name: string;
price: number;
option: T;
}
const m1: Mobile<object> = {
name: 's1',
price: 1000,
option: {
color: 'red'
}
}
const m2: Mobile<string> = {
name: 's1',
price: 1000,
option: 'none'
}
interface GenereicLogTextFn1 {
<T>(text: T): T;
}
function logText<T>(text: T): T {
return text;
}
let myString1: GenereicLogTextFn1 = logText;
interface GenereicLogTextFn2<T> {
(text: T): T;
}
let myString2: GenereicLogTextFn2<string> = logText;
OR 연산자와 같이 A 이거나 B이다
라는 의미의 타입을 의미한다. ( | 사용 )
function padLeft(value: string, padding: string | number) { // Union Type
if (typeof padding === "number") {
return Array(padding + 1).join(" ") + value;
}
if (typeof padding === "string") {
return padding + value;
}
throw new Error(`Expected string or number, got '${typeof padding}'.`);
}
padLeft("Hello world", 4); // returns " Hello world"
padding 파라미터에 any타입으로 선언하면 에러를 감지하지 못하지만 union type으로 선언한다면 string 이거나 number 타입 이외에는 에러를 감지한다.
여러 타입을 모두 만족하는 하나의 타입을 의미한다. ( & 사용 )
interface ErrorHandling {
success: boolean;
error?: { message: string };
}
interface ArtistsData {
artists: { name: string }[];
}
type ArtistsResponse = ArtistsData & ErrorHandling; // Intersection Type
const handleArtistsResponse = (response: ArtistsResponse) => {
if (response.error) {
console.error(response.error.message);
return;
}
console.log(response.artists);
};
handleArtistsResponse 함수의 매개변수인 ArtistsResponse는 ArtistsData & ErrorHandling 타입에 접근 가능
네트워크 에러 핸들링 시 유용하다고 함.