JavaScript
TypeScript 2
재키재키
2022. 6. 12. 14:35
1. call signatures
- TypeScirpt에서 함수를 작성할 때에 항상 parmeter type과 return type을 함께 정의해야 한다.
- call signature 즉 미리 함수에 대해 type을 작성하고 이후에 함수를 만들어 사용할 수 있다.
// 함수의 return type을 적지 않아도 된다,
const add1 = (a:number, b:number) => a + b
// call signatures : 함수에 마우스 올렸을 때 함수에 대해 알려주는 거
// 함수의 타입을 정의할 수 있다. 이는 parmeter, return 의 type을 미리 정의함을 말한다.
type Add = (a:number, b:number) => number
const add2:Add = (a, b) => a + b
2. overloading
- 여러개의 서로 다른 call signature를 가진 함수
- 함수에 여러가지 방법으로 parameter를 전달하고 싶을 때
- parmeter의 개수가 달라지면 ?(optional)임을 명시해야 한다.
// overloaing
// 여러개의 서로 다른 call signatures를 가진 함수
type Add = {
(a:number, b:number) : number
(a:number, b:string) : number
}
const add: Add = (a, b) => {
if(typeof b === 'string') return a
return a + b
}
// example
// nextjs : 밑의 두 함수는 서로 다른 parameter값으로 정확히 같은 일을 한다.
Router.push({
path:"/home"
})
Router.push("/home")
type Config = {
path: string,
staet: object
}
type Push = {
(path:string):void,
(config: Config):void
}
const push:Push = (config) => {
if(typeof config === "string") console.log(config)
else {
console.log(config.path, config.staet)
}
}
// 만약에 parmeter의 개수가 다른 call signature라면?
type Add = {
(a: number, b:number): number,
(a: number, b:number, c:number): number
}
const add:Add = (a, b, c?:number) => {
if(c) return a + b +c
return a + b
}
add(1, 2)
add(1, 2, 3)
3. polymorphism, generic
- generic을 사용하면 함수가 concerte type이 아닌 아닌 parameter를 받을 때 상황에 맞게 정의될 수 있게 한다.
- generic은 call signature를 요구하는 대로 매번 다르게 알아서 정의해준다.
- parameter를 any로 지정하는 것과는 다르다
- type SuperPrint = <T>(a: T[]) => T
- 여러개의 generic을 사용할 때에는 정의하고 순서에 맞게 paameter를 넣어주면 된다,
// polymorphism, generic
type SuperPrint = {
// (arr: number[]): void
// (arr: boolean[]): void,
// (arr: string[]): void,
// (arr: (number|string|boolean)[]): void
// 모두 이렇게 정의해야 한다고??
// generic 사용하자! -> 함수가 concrete type이 아닌 generic을 받을 때
<T>(arr: T[]): void
}
const superPrint: SuperPrint = (arr) => {
arr.forEach(i => console.log(i))
}
// type script가 매번 다르게 call signature를 유추해서 알려준다.
superPrint([1,2,3,4])
superPrint([true, false, true])
superPrint(["a", "b", "C"])
superPrint([1, 2, "a", true])
type SuperPrint2 = {
<T>(arr: T[]): T // generic 사용1
}
const superPrint2:SuperPrint = (arr) => arr[0]
const x = superPrint2([1,2,3])
const y = superPrint2([true, false, true])
const z = superPrint2(["a", "b", "C"])
// 여러개의 generic 사용, 순서에 맞게 parameter를 넣어준다.
type SuperPrint3 = <T, V>(a:T[], b:V) => T
const superPrint3: SuperPrint3 = (a,b) => {
console.log(b)
return a[0]
}
const x = superPrint3([1,2,3],"many generic")
- 더 많은 사용예시들....
// generic...
function superPrint<T>(a: T[]){
return a[0]
}
// generic을 사용! 아직 E는 정해지지 않았다.
type Player<E> = {
name: string,
extraInfo: E,
}
// generic E는 객체라고 알려주자.
const joony: Player<{favFood:string}> = {
name:"joony",
extraInfo: {
favFood: "hambe"
}
}
type JoonyExtra = {
favFood: string
}
// generic E가 JoonyExtra type이다!
type JoonyPlyaer = Player<JoonyExtra>
const hanbi: JoonyPlyaer = {
name: "hanbi",
extraInfo: {
favFood:"gimch"
}
}
type A = Array<number>
let a:A = [1,2 , 3]
function printAllNumbers(arr: Array<number>){
}