TpyeScriptlanguage

Strong versus Weak typing (type safety)

  • Strongly typed: Strongly typed languages do not allow any implicit type conversions

    • Advantage:
      1. Mistakes are exposed earlier
      2. Smarter code, more accurate coding (smart tips
      3. Refactoring code is more robust
      4. Reduce unnecessary type judgments
  • Weak typing: Any implicit type conversion can be allowed in weakly typed languages

    • Question:

      // You need to wait until the code is executed to find the error
      const obj = {};
      setTimeout(() = >{
          obj.foo()
      })
      
      // The function function may change
      function sum (a , b){
          return a + b
      }
      sum(100.100)
      sum(100.'100')
      
      // Causes an incorrect use of the object indexer
      const obj = {};
      obj[true] = 100;
      console.log(obj['true'])
      Copy the code

      Variable types are allowed to change at any time, not strong and weak type differences

Dynamic versus static typing (type checking)

  • Dynamic typing: The type of a variable is known only at run time, and it can change
  • Static typing: Variable declarations The type of a variable is unambiguous and unchangeable

The raw data type in TS

const a: string = 'a'

const b: number = 1

const c: boolean = true

const d: void = undefined

const e: null = null

const f: undefined = undefined

const g: symbol = Symbol(a)Copy the code

Object in TS

The Object type in TS refers not only to ordinary objects, but to all non-primitive data types (objects, arrays, functions).

const foo: object = function(){} / / / / [] {}
Copy the code

The array type in TS

// Two different ways to write it
const arr1: Array<number> = [1.2.3]

const arr2: number[] = [1.2.3]
Copy the code

Tuple Types in TS

Tuples: An array that specifies the number of elements and the type of each element

const tuple: [number, string] = [1.'foo']
Copy the code

An enumeration type in TS

// Variables in the enumeration can be left unassigned by default, increasing from 0 if no value is assigned, or from that value if the first value is assigned to a non-zero number by default
// If the variables in the enumeration are assigned to characters, the sequential increment does not occur, and the value of each variable needs to be specified
// The default enumeration mode intrudes into run-time code, that is, affects the compiled code, and the enumeration object is compiled as a two-way key-value function
// To avoid intrusion, you can use constant enumerations to declare the keyword before enum (const).
enum PostStatus {
    Draft = 0,
    UnPublished = 1,
    Published = 2
}



const post = {
    title: 'Hello TypeScript'.content:'TypeScript is a type superset of JavaScript'.status: PostStatus.Draft
}

Copy the code

Function types in TS

// declarative functions

function func1(a: number, b: string) :string {
    return 'func1'
}

// Optional parameter writing
function func1(a: number, b: string, c? : string) :string {
    return 'func1'
}

// Any number of arguments
function func1(. rest: number[]) :string {
    return 'func1'
}

// The way the function is expressed

const func2: (a: number, b: string) = > string = a: number, b: string): string {
    return 'func2'
}
Copy the code

Any type in TS

// TS does not type check any, which can lead to errors, so you should avoid using any

function stringify (value: any){
    return JSON.stringify(value)
}

Copy the code

Type Inference of TS

// TS will infer that the age type is number
let age = 18;


Copy the code

TS Type Assertion

const nums = [100.200.300.400]

/ / TS here will infer types for the number of res | is undefined
const res = nums.find(i= > i > 0)

// Because we know res must be number, we need to tell TS that res must be number. There are two ways

const num1 = res as number

const num2 = <number>res // This method is not recommended because there is confusion when using JSX here

Copy the code

TS Interfaces

An interface is a structure used to contract an object.

// Define an interface
interface Post {
    title: string; content: string; subTitle? : string;// Indicates an optional member
    readonly summary: string // readonly: read-only member
}

// Interface usage
function printpost(post: Post){
    console.log(post.title)
    console.log(post.content)
}

const hello: Post = {
    title:'hello'.contentL: 'This is a hello'.summary: 'Title Summary'
}
// An interface can be understood as defining a type that specifies which elements are required and the type of the specific element


// The dynamic member definition does not know what the specific members are

interface Cache {
    [key:string]: string
}

const cache:Cache = {
    a: 'a'
}

Copy the code

Basic use of the TS class

TS has enhanced the use of classes


  • Class attributes must be declared in ts. If the attribute does not have a default value, it must be assigned in the constructor
class Person {
    // class attributes must be declared first. If there is no default value for the attribute, the constructor must assign the value
    name: string, 
    age: number,
    construction(name: string, age: number) {
        this.name = name; 
        this.age = age;
    }
    sayHi(msg: string) : string {
        return 'hi'+ msg; }}Copy the code
  • Class access modifier

    • publicDefault value, public properties
    • privateA private property that can only be used inside a class and cannot be accessed externally
    • protectedSimilar toprivate; In contrast toprivateFor example, useprotectedIs accessible by an inherited class
      class Person {
      // class attributes must be declared first. If there is no default value for the attribute, the constructor must assign the value
      public name: string, 
      private age: number,
      protected gender: boolean,
      construction(name: string, age: number) {
          this.name = name; 
          this.age = age;
      }
      sayHi(msg: string) : string {
          return 'hi' + msg;
      }
    
      class Student extends Person {
          // constructor can also be modified with modifiers
          // The use of private here means that attributes of the Student class cannot be created externally using the new keyword, but instances can be created by implementing a static method in the class
          private constructor (name: string, age: number) {
              super(name, age);
              // Gender is a protected property, accessible in classes that inherit from Person
              console.log(this.gender);
          }
          
          static create(name: string, age: number){
              return new Student(name, age)
          }
      }
    Copy the code
  • The readonly property in TS

    class Person {
      // class attributes must be declared first. If there is no default value for the attribute, the constructor must assign the value
      public name: string, 
      private age: number,
      protected readonly gender: boolean, // readonly: the value can only be read and cannot be reassigned
      construction(name: string, age: number) {
          this.name = name; 
          this.age = age;
      }
      sayHi(msg: string) : string {
          return 'hi'+ msg; }}Copy the code
  • Class versus interface comparison

    • There may be common features between different classes, which we abstract out as interfaces
      interface Eat {
          eat (food: string) : void
      }
      interface Run {
          run (disrance: number) : void
      }
    
      // It is recommended that an interface define only one method (capability)
      /* interface EatAndRun { eat (food: string) : void run (disrance: number) : void } */
    
      class Person implement Eat.Run {
          eat (food: string): void {
              console.log('Eat gracefully:' + food)
          }
          run (distance: number): void {
              console.log('Walking upright' + distance)
          }
      }
    
      class Animal implement Eat.Run{
          eat (food: string): void {
              console.log('Eat without image:' + food)
          }
          run (distance: number): void {
              console.log('crawl' + distance)
          }
      }
    Copy the code
  • Abstract Classes Are similar to interfaces in that they are used to constrain subclasses to have certain members. In contrast to interfaces, abstract classes must also contain concrete implementations, while interfaces only contain constraints that do not include implementations. For large classes, abstract classes are recommended

      abstract class Animal implement Eat.Run{
          eat (food: string): void {
              console.log('Eat without image:' + food)
          }
          abstract run (distance: number): void
      }
    // An abstract class cannot use the new keyword to create instances, but can only subclass by inheritance
      class Dog extends Animal {
          run (distance: number) {
              console.log('Four Corners crawl' + distance)
          }
      }
    
      const d = new Dog()
      d.eat('bone')
      d.run(20)
    Copy the code
  • Generics is a characteristic of defining a class, function, or interface without defining a specific type until it is used. The point is to reuse code to a great extent

    // where T is the concrete type passed in for future use.
    function createArray<T> (length: number, value: T) :T {
        return Array<T>(length).fill(value);
    }
    
    const stringArray = createdArray<string>(3.'aaa')
    Copy the code
  • Type declaration

    • When using third-party plug-in libraries, you may encounter methods that do not define types (no type prompt is visible), so you can use type declarations
    import { camelCase } from 'lodash';
    
    declare function camelCase (input: string) :string// It can be used directly after being declared hereconst res = camelCase('hello world') // Many plugins have type declaration files, so you can install them. In addition, many plug-ins contain their own type declaration files that do not need to be installed or declared separatelyCopy the code