前言

TypeScript 的官网文档早已更新,但我能找到的中文文档都还停留在比拟老的版本。所以对其中新增以及订正较多的一些章节进行了翻译整顿。

本篇整顿自 TypeScript Handbook 中 「Indexed Access Types」 章节。

本文并不严格依照原文翻译,对局部内容也做了解释补充。

注释

咱们能够应用索引拜访类型(indexed access type)查找另外一个类型上的特定属性:

type Person = { age: number; name: string; alive: boolean };type Age = Person["age"];// type Age = number

因为索引名自身就是一个类型,所以咱们也能够应用联结、keyof 或者其余类型:

type I1 = Person["age" | "name"];  // type I1 = string | number type I2 = Person[keyof Person];// type I2 = string | number | boolean type AliveOrName = "alive" | "name";type I3 = Person[AliveOrName];  // type I3 = string | boolean

如果你尝试查找一个不存在的属性,TypeScript 会报错:

type I1 = Person["alve"];// Property 'alve' does not exist on type 'Person'.

接下来是另外一个示例,咱们应用 number 来获取数组元素的类型。联合 typeof 能够不便的捕捉数组字面量的元素类型:

const MyArray = [  { name: "Alice", age: 15 },  { name: "Bob", age: 23 },  { name: "Eve", age: 38 },]; type Person = typeof MyArray[number];       // type Person = {//    name: string;//    age: number;// }type Age = typeof MyArray[number]["age"];  // type Age = number// Ortype Age2 = Person["age"];   // type Age2 = number

作为索引的只能是类型,这意味着你不能应用 const 创立一个变量援用:

const key = "age";type Age = Person[key];// Type 'key' cannot be used as an index type.// 'key' refers to a value, but is being used as a type here. Did you mean 'typeof key'?

然而你能够应用类型别名实现相似的重构:

type key = "age";type Age = Person[key];

最初讲一个实战案例:

假如有这样一个业务场景,一个页面要用在不同的 APP 里,比方淘宝、天猫、支付宝,依据所在 APP 的不同,调用的底层 API 会不同,咱们可能会这样写:

const APP = ['TaoBao', 'Tmall', 'Alipay'];function getPhoto(app: string) {  // ...}  getPhoto('TaoBao'); // okgetPhoto('whatever'); // ok

如果咱们仅仅是对 app 束缚为 string 类型,即便传入其余的字符串,也不会导致报错,咱们能够应用字面量联结类型束缚一下:

const APP = ['TaoBao', 'Tmall', 'Alipay'];type app = 'TaoBao' | 'Tmall' | 'Alipay';function getPhoto(app: app) {  // ...}  getPhoto('TaoBao'); // okgetPhoto('whatever'); // not ok

但写两遍又有些冗余,咱们怎么依据一个数组获取它的所有值的字符串联结类型呢?咱们就能够联合上一篇的 typeof 和本节的内容实现:

const APP = ['TaoBao', 'Tmall', 'Alipay'] as const;type app = typeof APP[number];// type app = "TaoBao" | "Tmall" | "Alipay"function getPhoto(app: app) {  // ...}  getPhoto('TaoBao'); // okgetPhoto('whatever'); // not ok

咱们来一步步解析:

首先是应用 as const 将数组变为 readonly 的元组类型:

const APP = ['TaoBao', 'Tmall', 'Alipay'] as const;// const APP: readonly ["TaoBao", "Tmall", "Alipay"]

但此时 APP 还是一个值,咱们通过 typeof 获取 APP 的类型:

type typeOfAPP = typeof APP;// type typeOfAPP = readonly ["TaoBao", "Tmall", "Alipay"]

最初在通过索引拜访类型,获取字符串联结类型:

type app = typeof APP[number];// type app = "TaoBao" | "Tmall" | "Alipay"

TypeScript 系列

  1. TypeScript 之 Narrowing
  2. TypeScript 之 More on Functions
  3. TypeScript 之 Object Type
  4. TypeScript 之 Generics
  5. TypeScript 之 Keyof Type Operator
  6. TypeScript 之 Typeof Type Operator

微信:「mqyqingfeng」,加我进冴羽惟一的读者群。

如果有谬误或者不谨严的中央,请务必给予斧正,非常感激。如果喜爱或者有所启发,欢送 star,对作者也是一种激励。