Typescript进阶Day6-Day7

67 阅读3分钟

偷懒了俩天..继续.. 对应小册7-8课

Typescript类型工具

前面了解的类型和内置类型是积木块,需要用一些类型工具来拼装出所需要的类型。 按照使用目的来分,类型工具可以分为类型创建类型安全保护两类。

类型创建

类型别名

类型别名使用了泛型就可以作为工具类。

索引类型

索引签名类型

主要应用在接口或类型别名中,通过以下语法来快速声明一个键值类型一致的类型结构:

interface AllStringTypes {
[key: string]: string;
}

type AllStringTypes = {
[key: string]: string;
}
  • 因为在js中,对于obj[prop]形式的访问将数字索引访问转换成字符串索引访问。所以对于数字类型和symbol类型的键,也是可以声明的。
const foo: AllStringTypes = {
    "linbudu": "599",
    599: "linbudu",
    [Symbol("ddd")]: 'symbol',
}
  • 索引签名类型也可以和具体的键值对类型声明并存,但是也要符合索引签名类型的声明。
interface AllStringTypes {
// 类型“number”的属性“propA”不能赋给“string”索引类型“boolean”。
propA: number;
[key: string]: boolean;
 }

索引类型查询

可以将对象所有键转换成对应的字面量类型,然后再组合成联合类型。

 interface Foo {
     day:1,
     599:2
  }
  type Fookeys = keyof Foo // "day" | 599

索引类型访问

通过键的字面量类型('propA')访问这个键对应的键值类型(number

interface NumberRecord {
  [key: string]: number;
}

type PropType = NumberRecord[string]; // number

注意:如果没有使用索引签名类型,就只能通过具体的字面量来访问。

映射类型

通常和索引签名类型一起使用。 基于键名映射到键值类型。

type Stringfy<T> = {
    [k in keyof T] : string;
}

interface Foo {
  prop1: string;
  prop2: number;
  prop3: boolean;
  prop4: () => void;
}

type StringifiedFoo = Stringify<Foo>;

// 等价于
interface StringifiedFoo {
  prop1: string;
  prop2: string;
  prop3: string;
  prop4: string;
}

类型安全

类型查询操作符

js、ts有各自的typeof,都是用来检查并返回变量类型的。 在ts中,typeof返回的是最窄的推导程度(字面量类型)。 为了区分类型层和逻辑层中的typeof,类型查询操作符后是不允许使用表达式的。

类型守卫

基于将判断逻辑封装起来提取到函数外部进行复用的情况,ts的类型控制流分析能力不足,引入了is关键字来显性的提供类型信息。

function isString(input: unknown): input is string {
  return typeof input === "string";
}

function foo(input: string | number) {
  if (isString(input)) {
    (input).replace("linbudu", "linbudu599")
  }
  if (typeof input === 'number') { }
  // ...
}

如果函数返回true,则is关键字前的入参类型就会被判断为is后的预期类型。

基于in与instanceof的类型保护

in

  • 可以是不同名属性(in)
interface Foo {
  kind:'foo',
  foo: string;
  fooOnly: boolean;
  shared: number;
}

interface Bar {
  kind:'bar',
  bar: string;
  barOnly: boolean;
  shared: number;
}

function handle(input: Foo | Bar) {
  if ('foo' in input) {
    input.fooOnly;
  } else {
    input.barOnly;
  }
}
  • 可以是同名属性的字面量类型的差异
function handle(input: Foo | Bar) {
  if (input.kind === 'foo') {
    input.fooOnly;
  } else {
    input.barOnly;
  }
}

instanceof

判断的是原型级别的关系

assert类型断言守卫

没太看懂意义 看看后面看完react源码能不能遇到 没遇到就不管了。