This is the 17th day of my participation in the August Text Challenge.More challenges in August

Type of protection

In TypeScript, conditional blocks have another feature: narrowing the type range (sort of like assertion) based on the result of the judgment logic. This feature is called type protection and triggers conditions:

  • Logical conditional statements: if else elseif
  • Specific keywords: typeof instanceof in….

typeof

We know that typeof can return a certain typeof data, and TypeScript recognizes typeof as type-protected in the if and else blocks to infer the appropriate type

function fn(a:string|number){ a.substring(1); If (typeof a === 'string'){a.substring(1); }else{ a.toFixed(1) } }Copy the code

instanceof

Like Typeof, Instanceof is recognized by TypeScript as type-protected

function fn(a:Date|Array<any>){ if(a instanceof Array){ a.push(1); }else{ a.getFullYear(); }}Copy the code

in

In is the same thing

interface IA { 
    x: string; 
    y: string; 
} 

interface IB { 
    a: string; 
    b: string; 
}

function fn(arg:IA | IB){
    if('x' in arg){
        arg.x; //ok
        arg.a; //error
    }else{
        arg.a; //ok
        arg.x; //error
    }
}
Copy the code

Literal-type protection

If the type is a literal type, you can also infer from the literals of that literal type

interface IA { type: 'IA'; x: string; y: string; } interface IB { type: 'IB'; a: string; b: string; } function fn(arg: IA | IB) { if (arg.type === 'IA') { // ok arg.x; // error arg.a; } else { // ok arg.a; // error arg.x; }}Copy the code

Custom type protection

In some cases, if none of the above methods are sufficient, you can customize the type protection rules

function canEach(data:any):data is Element[] | NodeList{ return data.forEach ! == undefined; } function fn(elements:Element[]|NodeList|Element){ if(canEach(elements)){ elements.forEach((el:Element)=>{ el.classList.add('box') }); }else{ elements.classList.add('box') } }Copy the code

Data Element is [] | NodeList is a type of predicate, format for: xx is xx, return to this type of function can be TypeScript identification for the type of protection

Type of operation

TypeScript provides ways to manipulate type data, but it’s important to note that type data can only be used as type data, not as data in programs. There are two different types of data: one for compilation and one for execution

typeof

In TypeScript, Typeof serves two purposes:

  • Gets the type of data
  • The type of data to capture
Let STR = 'STR' // let string = 'string' lte t = typeof STR; Type strType = typeof STR; let str2: strType = 'str'; let str3: typeof str1 = 'str';Copy the code

key of

Gets a collection of all keys for the type

interface Person { name: string; age: number } type personKeys = keyof Person; / / equivalent: type personKeys = "name" | "age" let p1 = {name: 'zMouse, age: 35} function getPersonVal (k: personKeys) { return p1[k]; } / * * : to identify the function getPersonVal (k: 'name' | 'age') {return p1 [k]. } */ getPersonVal('name'); / / correct getPersonVal (" gender "); / / errorCopy the code

in

Internal use of for… In traverses the type

interface Person { name: string; age: number; } type personKeys = keyof Person; type newPerson = { [k in personKeys]: number; / * * equivalent [k in the 'name' | 'age'] : number; You can also write [k in keyof Person]: number; */ } /** type newPerson = { name: number; age: number; } * /Copy the code

Note: The type value after in must be string or number or symbol

Type is compatible

TypeScript’s type system is based on structural subtypes, which are different from nominal types (e.g. Java) whose datatype compatibility or equivalence is determined by explicit declarations or type names). This type system based on structure subtypes is based on grouping structures, and as long as there are members of the same type, the two types are compatible.

class Person { name: string; age: number; } class Cat { name: string; age: number; } function fn(p: Person) { p.name; } let xiaohua = new Cat(); // ok, because the structure of Cat type is similar to the structure of Person type, they are compatible fn(Xiaohua);Copy the code