持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第21天,点击查看活动详情
1. 引言
今天我们接着继续Ts基础篇的题型练习
https://github.com/type-challenges/type-challenges/blob/main/README.zh-CN.md 提供的TypeScript 类型体操姿势合集题型,目的是为了让大家更好的了解TS的类型系统,编写自己的类型工具,或者单纯的享受挑战的乐趣!
接下来我们就由简单入深,开始一步步闯关学习
2. 题型
1.在类型系统里实现通用的 Array.push 。 思路: 首先约束泛型变量T属于数组,在通过[...T,U]进行数组合并 解答:
type PushFun<T extends any[], U> = [...T,U]
type Demo = PushFun<[], 1> // type Demo = [1]
type Demo2 = PushFun<[1, 2], '3'> // type Demo2 = [1, 2, "3"]
type Demo3 = PushFun<['1', 2, '3'], boolean> // type Demo3 = ["1", 2, "3", boolean]
2.实现类型版本的 Array.unshift。 思路: 首先约束泛型变量T属于数组,在通过[U,...T]进行数组合并(上一题型调换下顺序就ok了) 解答:
type Demo = Unshift<[], 1> // type Demo = [1]
type Demo2 = Unshift<[1, 2], 0> // type Demo2 = [0, 1, 2]
type Demo3 = Unshift<['1', 2, '3'], boolean> // type Demo3 = [boolean, "1", 2, "3"]
3.实现内置的 Parameters 类型,而不是直接使用它,从函数类型type的形参中使用的类型构造元组类型
测试用例:
type T0 = Parameters<() => string>; // type T0 = []
type T1 = Parameters<(s: string) => void>; // type T1 = [s: string]
type T2 = Parameters<<T>(arg: T) => T>; // type T2 = [arg: unknown]
type T3 = Parameters<typeof f1>; // type T3 = [arg: {a: number;b: string;}]
type T4 = Parameters<any>; // type T4 = unknown[]
type T5 = Parameters<never>; // type T5 = never
type T6 = Parameters<string>; // Type 'string' does not satisfy the constraint '(...args: any) => any'.
// type T6 = never
type T7 = Parameters<Function>; // Type 'Function' does not satisfy the constraint '(...args: any) => any'.
// Type 'Function' provides no match for the signature '(...args: any): any'.
// type T7 = never
思路: 使用infer R放置函数形参位置,用于推断获取形参类型,在通过extends条件判断推出形参类型,如果形参值多个,并且是多类型则返回数组(类型系统:元祖)
解答:
type MyParameters<T extends (...args: any[]) => any> = T extends (...args: infer R) => any ? R : never
const foo = (arg1: string, arg2: number): void => {}
const bar = (arg1: boolean, arg2: { a: 'A' }): void => {}
const baz = (): void => {}
type Demo = MyParameters<typeof foo> // type Demo = [string, number]
type Demo2 = MyParameters<typeof bar> // type Demo2 = [boolean, { a: 'A' }]
type Demo3 = MyParameters<typeof baz> // type Demo3 = []