preface

There are a number of generic tools built into Typescript by default that make defining types more flexible and efficient. This article will introduce the use of common generic tools, as well as the implementation of the principle of the corresponding analysis, if there are mistakes, please point out.

Partial<T>

Effect: Makes an attribute passed to object type T optional.

Example:

interface Person {
  name: string;
  age: number;
}

const tom: Partial<Person> = {
  name: "Tom"};Copy the code

Partial < Person > is equivalent to

interfacePerson { name? :string; age? :number;
}
Copy the code

Implementation principle:

  1. By keywordkeyofConverts the key value of the passed object type to the union type.
  2. By keywordinIterate over the union type, that is, the key value of an object.
  3. Attributes of an object are converted to optional attributes through type mapping
type MyPartial<T> = {
  [P inkeyof T]? : T[P]; };Copy the code

Readonly<T>

Effect: Changes the incoming object type T property to a read-only property.

Example:

interface Person {
  name: string;
  age: number;
}

const tom: Readonly<Person> = {
  name: "Tom".age: 18;
};

tom.age = 22 // error
Copy the code

Readonly < Person > is equivalent to

interface Person {
  readonly name: string;
  readonly age: number;
}
Copy the code

Implementation principle:

Similar to Partial:

  1. By keywordkeyofConverts the key value of the passed object type to the union type.
  2. By keywordinIterate over the union type, that is, the key value of an object.
  3. Attributes of an object are converted to read-only attributes through type mapping
type Readonly<T> = {
  readonly [P in keyof T]: T[P];
};
Copy the code

Required<T>

Effect: Changes the incoming object type T property to a required property.

Example:

interfacePerson { name? :string; age? :number;
}

let tom: Required<Person>

tom = {
  name: "Tom".age: 18;
};
// ok

tom = {
  name: "Tom"};// error
Copy the code

Implementation principle:

Similar to Partial:

  1. By keywordkeyofConverts the key value of the passed object to an enumerated type.
  2. By keywordinIterate over enumerated types, that is, iterate over the key value of an object.
  3. Through type mapping, and then unified through-Modifier removal?Modifier to convert toMandatory state.
type Required<T> = {
  Required [P in keyof T]: T[P];
};
Copy the code

Record<K,T>

It is used to generate a collection of object types with the property name K and the property value type T.

Example:

// Quickly generate a Person object
type Person = Record<"name" | "country".string>;

const Tom: Person = { name: "Tom".country: "America" };
Copy the code

Implementation principle:

  1. throughK extends keyof anyKParameter to constrain to any typeanyThe key values.
  2. throughinSet of key valuesKIterate, and generate typeTIs a collection of key-value pairs.
type MyRecord<K extends keyof any, T> = {
  [P in K]: T;
};
Copy the code

Exclude<T,K>

Function: Excludes all types from type T that can be assigned to type U.

Example:

/ / from "a" | | "b" "c" tossed off "a" type
type T1 = Exclude<"a" | "b" | "c"."a">;
// T1 = "b" | "c"

From the string / / | number | tossed off a Boolean type string
type T2 = Exclude<string | number | boolean.string>;
// T2 = number | boolean
Copy the code

Implementation principle:

  1. By condition typeT extends U ? never : TTParameter discrimination:
    • ifTCan be assigned toU, then returnnever(That is, excludeT).
    • ifTCannot be assigned toU, then returnT.
  2. throughDistributed condition typeIf theTIs the union type, then the result of the condition type is distributed asThe joint type.
type Exclude<T, U> = T extends U ? never : T;
Copy the code

Extract<T,K>

Function: Extracts all types from type T that can be assigned to type U, as opposed to Exclude.

Example:

/ / from "a" | | "b" "c" extract "a" type
type T1 = Extract<"a" | "b" | "c"."a">;
// T1 = "a"

From the string / / | number | can be derived from the Boolean type string
type T2 = Extract<string | number | boolean.string>;
// T2 = string

type T3 = Extract<string | (() = > void), Function>;
// type T3 = () => void;
Copy the code

Implementation principle:

Similar to Exclude:

  1. By condition typeT extends U ? never : TTParameter discrimination:
    • ifTCan be assigned toU, then returnT.
    • ifTCannot be assigned toU, then returnnever(That is, excludeT).
  2. throughDistributed condition typeIf theTIs the union type, then the result of the condition type is distributed asThe joint type.
type Extract<T, U> = T extends U ? T : never;
Copy the code

Pick<T,K>

Action: In T, pick K attribute.

Example:

interface Person {
  name: string;
  age: number;
}

// Pick the name attribute from Person
type PickPerson = Pick<Person, "name">;

const tom: PickPerson = {
  name: "Tom"};Copy the code

Implementation principle:

  1. throughK extends keyof TKParameter, and constrain it to beTWithin the key value range of.
  2. throughinSet of key valuesKIterate, and generate typeTIs a collection of key-value pairs.
type Pick<T, K extends keyof T> = {
  [P in K]: T[P];
};
Copy the code

Omit<T,K>

Action: In T, the K attribute is removed.

Example:

interface Person {
  name: string;
  age: number;
}

// Remove the name attribute from Person
type OmitPerson = Pick<Person, "name">;

const tom: PickPerson = {
  age: 18};Copy the code

Implementation principle:

  1. throughK extends keyof TKParameter, and constrain it to beTWithin the key value range of.
  2. throughExclude<keyof T, K>Set of typesTIn theKType excluded.
  3. throughPick<T,Exclude<keyof T, K>>TPick out and excludeKTProperties.
type Omit<T, K extends keyof any> = Pick<T, Exclude<keyof T, K>>;
Copy the code

ReturnType<T>

Gets the return type of a function.

Example:

type Fun = () = > string;

// Get the type of Fun returned
type T1 = ReturnType<Fun>; // T1 = string

type T2 = ReturnType<() = > { x: number; y: number} >.// T2 = { x: number, y: number }
Copy the code

Implementation principle:

  1. throughextendsTParameter constraint,(... args: any) => anyRepresents a function type, i.eTThe parameter type must be oneFunction types.
  2. T extends U ? X : YIs the condition type (note the constraint and the previous oneextendsMake a distinction), among themTIs a generic parameter,UConditions section.XIs the result that meets the condition,YIs an unqualified return result.
  3. Inference typeinferThe condition () function declares a condition inside a condition typeType variable.(... args: any) => infer RIs of the condition typeConditions section, which declares a type variableRIs used to store the return type of the function.
  4. T extends (... args: any) => any> = T extends (... args: any) => infer R ? R : anySaid:
    • ifTIs a function type ((... args: any) => infer R), returnsR, the return type of the function.
    • ifTNot function type ((... args: any) => infer R), returnsany.
type ReturnType<T extends(... args:any) = >any> = T extends (
  ...args: any
) => infer R
  ? R
  : any;
Copy the code

The resources

  • TypeScript Chinese manual
  • TypeScript built-in tool generics