dljia
  • 前言
  • es6
    • promise
    • 箭头函数
  • http相关
    • ajax请求中contentType和dataType
    • async和defer的区别
    • cookie、session和token
    • http协议介绍
    • http缓存
    • 转发和重定向
  • js
    • 1-js深浅复制
    • 10-节流防抖
    • 11-Promise常见手写
    • 2-js函数值传递
    • 3-js原型链详解
    • 4-js基础讲解this篇
    • 5-call、apply和bind
    • 6-js中的继承
    • 7-闭包与立即执行函数
    • 8-js事件循环
    • 9-js模块化
  • react
    • React-diff
    • React-fiber
    • React组件设计规则
    • mvc与mvvm
    • react-router
    • react懒加载
    • redux
    • setState源码分析
    • webpack+react从0项目构建
  • ts
    • Typescript编程书籍导读
    • 体操基础
  • 其他
    • gitbook简易配置教程
    • gitbook转pdf电子书
  • 微前端
    • pnpm
    • qiankun
    • single-spa源码分析
    • 几种微前端架构的选型
  • 转载
    • interview-1
    • interview-2
    • interview-3
    • 经验好文
  • 项目经验
    • 23年总结
    • [Arkts 学习笔记](项目经验/Arkts 学习笔记.md)
    • Grafana插件
    • JSDoc
    • electron-builder构建的安装包,安装时通过nsis脚本自动导入注册表
    • overflow-yautohiddenscroll和overflow-xvisible组合渲染异常
    • webpack
    • 前端工程化
    • 前端性能优化思路
    • 前端性能监控工具
    • 前端架构
    • 前端登录流程
    • 前端监控原理
    • 团队管理
    • 基于node实现简单server
    • 如何对业务进行深挖
    • 如何拉齐横向
    • 如何画图
    • 如何记录
    • 组件库
Powered by GitBook
On this page

Was this helpful?

  1. ts

体操基础

体操全集: https://github.com/type-challenges/type-challenges/blob/main/README.zh-CN.md

  1. Partial

    // Partial<T>将T的所有属性变成可选的。
    type Partial<T> = {
        [P in keyof T]?: T[P];
    }

    解释:

    1. in: in的用法是要用在类型遍历中形如上图这种{} 下 in 后面要是一个string、number、symbol联合类型,比如你可以keyof '1213'|'123123'|'13123' 但是不能p in [];

    2. keyof 是将一个接口(interface)或者类型(type)转变成他的key的联合类型

    3. T[p] 类似于js本身语法 T是个对象,P是他的key T[p] 就是他原来的值

  2. Exculde

        // Exculde<T, U>排除联合类型T 中 属于U的类型
        type Exculde<T, U> = T extends U ? never : T;
    
    

    解释:

    1. never 联合其他类型是没有never的

    2. T extends U ?never : T 属于条件类型 知识点:分布式条件类型

    这里有个思考就是1 的解题思路是{} {}中遍历key的形式。2的解题思路是条件类型 他俩有什么区别? 答 1 是对接口中key的筛选或处理,比如Pick(筛选出符合条件的key)、Record(给key赋值),2 是对联合类型的筛选 比如Exculde(例如:将'a'|'b' 筛选成'a')

  3. Require 将类型T所有属性设为require

    type Require<T> = {
         [p in keyof T]-?: T[p];
    }
  4. Pick<T, K> 从类型T 中挑选部分属性K 来构造新的类型

    
    type Pick<T, K> = {
         [p in keyof K]: T[p];
    }
  5. Extract<T, U> 从类型T中提取所有可以赋值给U的类型

    type Extract<T, U> = T extends U ? T : never;
  6. Omit<T, K> 从类型T中剔除所有能赋值给K的属性

    
    type Omit<T, K> = {
        [p in Exculde<keyof T, K>] : T[p];
    }
    
    // 但是这里面还有一种更有意思的写法 值得注意的是这里 as 对 T 起到了收敛子集的作用
    type Omit<T, K> = {
        [p in K as (T extends K ? never: T)] : T[p]
    }
    // 另外还有一种更长用的
    type OmitV<T, K> = {
        [p in keyof T as (T[p] extends K ? p : never)]: T[p];
    }
  7. NonNullable 从T中剔除null和undefined

  8. ReturnType

    type ReturnType<T extends (...arg: any) => any> = T extends (...arg:any) => infer R ? R : any;

    infer 这个东西必须用到条件语句中,用来推断。而且他有自己的作用域

  9. 实现一个判断startWith<T, U>

    // 网上流行的版本   其中string做为特殊关键字参与了结构;
    type startWith<Prefix> = `${Prefix}${string}`;
    
    type a = '/as'
    
    type b = a extends startWith<'/'> ? true; false;
    // 自己实现的版本
    type startWith<T, U extends string> = T extends `${U}${infer R}` ? true: false;
    
    type c = startWith<a, '/'>
  10. 使用映射类型实现window.addEvent

    type EventType1 = {
        target: Element;
    }
    
    type EventType2 = {
        target: HTMLInputElement;
    }
    
    type EventFunctionMap = {
        type1: EventType1;
        type2: EventType2;
    }
    
    type EventList = keyof EventFunctionMap;
    
    type addEvent<T extends EventList> = (
        type: T,
        listener: (
            arg:  EventFunctionMap[T],
        ) => void,
    ) => void;
    
    // 附上一个 不用映射类型的
    
  11. PickByType

    type OnlyBoolean = PickByType<{
    name: string
    count: number
    isReadonly: boolean
    isEnable: boolean
    }, boolean> // { isReadonly: boolean; isEnable: boolean; }
    
    // 实现:
    type PickByType<T, U> = {
        [K in keyof T as T[K] extends U ? K : never]: T[K]
    }
    

    很有意思的是拿as 约束了 key遍历的数量

  12. Mutable

    // Mutable 把所有的属性改为非只读,即去掉readonly 可以使用-操作符
    type Mutable<T extends object> = {
        -readonly [K in keyof T]: T[K]
    }
  13. Length of String

    type Split<S extends string> = S extends `${infer F}${infer R}` ? [F, ...Split<R>] : []
    
    type LengthOfString<S extends string> = Split<S>['length']

    思路: ts支持通过length变量取数组的长度,所以核心本质是字符串转数组,然后取长度; 另外ts中迭代基本就是模拟计算机手动压栈的过程;

PreviousTypescript编程书籍导读Next其他

Last updated 1 year ago

Was this helpful?