TypeScript

作者: 丽__ | 来源:发表于2021-05-14 09:36 被阅读0次

    一、TypeScript 概述(JavaScript的超集、扩展集)

    image.png
    • 任何一种JavaScript运行环境都支持
    • 功能更为强大,生态更为健全,更完善
    • Angular 、Vue3.0 使用TypeScript取代flow
    • 前端领域中的第二语言
    • 缺点:本身多了很多概念,项目初期,TypeScript会增加一些成本
    • 好处:属于【渐进式】

    二、TypeScript 快速上手

    • 安装yarn
    npm install -g yarn
    
    • 查看yarn版本
    yarn -v
    
    • 初始化package.json文件,用来管理依赖项
    npm init -y
    
    • 安装 typescript
    yarn add typescript --dev
    
    • 运行会生成对应的js
      会自动去除:number类型限制和编译成对应的js
    yarn tsc .\01-getting-started.ts
    

    三、TypeScript 配置文件

    • 使用命令yarn tsc --init自动生成tsconfig.json的配置文件文件
    yarn tsc --init
    

    配置部分tsconfig.json文件


    image.png
    • 终端运行 tsc,会将src下的文件编译输出到dist目录下

    四、TypeScript 原始类型

    /**
     * 在非严格模式(strictNullChecks)下
     * string,number,boolean都可以为空
     * const d:string =null
     * const d:number = null
     * const d:boolean = null
     *  */ 
    const d: null = null;
    const e: void = undefined;
    const f: undefined = undefined;
    
    /**
     * Symbol是ES2015标准中定义的成员
     * 使用它的前提必须确保有对应的ES2015库的引用
     * 也就是 tsconfig.json中的lib选项必须包含ES2015
     */
    const h: symbol = Symbol();
    

    五、TypeScript 标准库声明

    • 标准库就是内置对象所对应的声明
      当tsconfig.json中target为“es5”时,const h: symbol = Symbol();会报错,因为es5标准中没有Symbol,解决方法,在tsconfig.json中的lib添加["ES2015"],同理console.log在浏览器当中是BOM所提供的,而在TypeScript中把BOM 和DOM都归结到DOM一个标准库中,所以lib中需要追加["DOM"]
    image.png

    六、TypeScript 中文错误消息

    • 可以使用中文的错误消息
    yarn tsc --locale zh-CN
    

    七、TypeScript 作用域问题

    //不同文件定义相同类型的对象 会报错
    
    // 作用域问题
    (function () {
      const a = 123;
    });
    
    //或者
    const a = 123;
    export {};//作为模块导出,确保跟其他示例没有冲突
    
    

    八、TypeScript Object类型

    TypeScript中的Object类型并不单指普通的对象类型,而是泛指非原始类型,也就是对象,数组和函数

    export {}; //作为模块导出,确保跟其他示例没有冲突
    
    const foo: object = function () {}; //  []   {}
    
    const obj: { foo: number; bar?: string } = { foo: 1 };
    

    九、TypeScript 数组类型

    const arr1: Array<number> = [1, 2, 3];
    
    const arr2: number[] = [1, 2, 3];
    
    function sum(...args: number[]) {
      return args.reduce((prev, current) => prev + current, 0);
    }
    
    

    十、TypeScript 元组类型

    export {};
    const tuple: [number, string] = [12, "张三"];
    
    const [age, name] = tuple;
    
    Object.entries({
      foo: 123,
      bar: 22,
    });
    

    十一、TypeScript 枚举类型

    // 枚举类型
    export {};
    // 旧
    const postStatus = {
      draft: 0,
      unPublished: 1,
      pbulished: 2,
    };
    
    // 常量枚举
    const enum PostStatus2 {
      draft = 0,
      unPublished = 1,
      pbulished = 2,
    }
    
    const enum PostStatus3 {
      draft = 4, //默认从0开始,给了默认数值之后从当前数值开始增加
      unPublished,
      pbulished,
    }
    
    enum PostStatus4 {
      draft = 'fds',//可以是字符串  每个都需要填写
      unPublished = 1,
      pbulished = 2,
    }
    
    const post = {
      title: "hello TypeScript",
      content: "Typescript is a typed superset of JavaScript",
      status: postStatus.draft,
    };
    

    编译过后js文件中的枚举不会移除掉,使用常量枚举则可以移除

    image.png

    十二、TypeScript 函数类型

    // 函数类型
    
    export {}; //确保和其他示例成员没有冲突
    
    // 不确定参数放在最后  使用? 表示
    function fun1(a: number, b: number, c?: number) {
      return "func1";
    }
    fun1(1, 2);
    
    // 可以传递更多不确定参数请在最后使用...reset
    function fun2(a: number, b: number, ...rest: number[]) {
      return "func1";
    }
    fun2(1, 2, 3, 4, 5, 6, 7);
    
    // 函数表达式对应的限制
    // 参数和返回值的限制
    const fun3: (a: number, b: number) => string = function (
      a: number,
      b: number
    ): string {
      return "fun3";
    }; 
    

    十三、TypeScript 任意类型

    export {}; //确保和其他示例成员没有冲突
    
    function stringify(value: any) {
      return JSON.stringify(value);
    }
    
    stringify(1);
    stringify("fdsf");
    stringify(true);
    
    // any是不安全的
    
    

    十四、TypeScript 隐式类型推断

    export {}; //确保和其他示例没有成员冲突
    
    let age = 18; //相当于添加了number的类型注解
    
    // age = 'jk';//不能再将string类型赋值给number类型对象
    
    let foo;//相当于添加了类型为any的类型注解
    
    foo = 100;//可以重新赋值任意类型
    foo = "string";
    
    

    建议为每个变量添加明确的类型注解

    十五、TypeScript 类型断言

    export {}; //确保跟其他示例没有成员冲突
    
    const nums = [110, 120, 130, 140];
    
    const res = nums.find((i) => i > 0);
    console.log(res); //typescript推断类型为number或undefined
    
    // 方式一
    const num1 = res as number; //断言为number类型
    // 方式二
    const num2 = <number>res; //断言为number,JSX下不能使用
    

    十六、TypeScript 接口

    export {}; //确保和其他示例中没有成员冲突
    
    // 定义接口
    interface Post {
      title: string;
      content: string;
    }
    
    function printPost(data: Post) {
      console.log(data.title);
      console.log(data.content);
    }
    
    printPost({
      title: "hello",
      content: "Typescript",
    });
    
    

    接口就是用来约束对象的结构,一个对象去实现一个接口,必须要拥有这个接口中所有的成员

    十七、TypeScript 接口补充

    // 定义接口
    interface Post {
      title: string;
      content: string;
      subtitle?: string; //可选成员   添加  ?
      readonly summary: string; //只读 不可更改
    }
    
    const hello: Post = {
      title: "hello",
      content: "fds",
      summary: "只读,不能修改",
    };
    
    // hello.summary = 'other';//不能修改
    
    interface cache {
      [key: string]: string;
    }
    
    const cache1: cache = {};
    
    // cache1.1 ='value';//只能为string
    cache1.foo ='value'
    cache1.boo ='valued'
    

    十八、TypeScript 类的基本使用

    /**
     * 类:描述一类具体事务的抽象特征
     * ES6以前,函数 + 原型 模拟实现类
     * ES6开始,JavaScript中有了专门的class
     * TypeScript 增强了class 的相关语法
     */
    
    export {};
    
    class Person {
      name: string; //  = '初始值'
      age: number;
      constructor(name: string, age: number) {
        this.name = name;
        this.age = age;
      }
      sayHi(msg: string): string {
        console.log(`I am ${this.name}`);
        return "返回类型为string";
      }
    }
    
    

    十九、TypeScript 类的访问修饰符

    • public 公有
    • private 私有
    • protected 只能在子类成员中访问
    class Person {
      public name: string; //  = '初始值' public 公有属性
      private age: number; //私有属性
      protected gender: boolean; //只能在子类成员中访问
      constructor(name: string, age: number) {
        this.name = name;
        this.age = age;
        this.gender = true;
      }
      sayHi(msg: string): string {
        console.log(`I am ${this.name}`);
        return "返回类型为string";
      }
    }
    
    const tom = new Person("tom", 19);
    console.log(tom.name);
    // console.log(tom.age);//age已经设置为私有成员,不能访问
    // console.log(tom.gender); //也不能访问
    
    // 创建子类继承Person
    class Student extends Person {
      // 构造器添加private 外部不能访问,可以在内部添加静态方法创建实例
      private constructor(name: string, age: number) {
        super(name, age);
        console.log(this.gender); //可以访问
      }
      //   创建静态类外部可访问并且使用其中返回的创建实例方法
      static created(name: string, age: number) {
        return new Student(name, age);
      }
    }
    
    const jack = Student.created("jack", 20); //可以使用静态方法
    console.log(jack.name);
    

    二十、TypeScript 类的只读属性

    • readonly
      当readonly 和访问修饰符同时存在,readonly 写在访问修饰符的后面
    protected readonly  gender: boolean; //只能在子类成员中访问 并且只读不能修改
    

    二十一、TypeScript 类与接口

    • 使用 implements 关键字
    // 类与接口
    
    interface eat {
      eat(food: string): void;
    }
    interface run {
      run(distance: number): void;
    }
    
    class Person implements eat, run {
      eat(food: string): void {
        console.log(`优雅的进餐:${food}`);
      }
      run(distance: number): void {
        console.log(`直立行走:${distance}`);
      }
    }
    class Animal implements eat, run {
      eat(food: string): void {
        console.log(`大口大口:${food}`);
      }
      run(distance: number): void {
        console.log(`爬行${distance}`);
      }
    }
    
    

    二十二、TypeScript 抽象类

    • abstract
    • 在class前面添加abstract,为抽象类,当前类只能继承不能创建(new Animal)
    • /当父类中有抽象方法,继承的子类要去实现
    export {}; //确保跟其他示例没有成员冲突
    
    // 在class前面添加abstract,为抽象类,当前类只能继承不能创建(new Animal)
    abstract class Animal {
      eat(food: string): void {
        console.log(`大口大口:${food}`);
      }
      //抽象方法不需要方法体  也就是{ }
      //当父类中有抽象方法,继承的子类要去实现
      abstract run(distance: number): void;
    }
    
    class Dog extends Animal {
      //当父类中有抽象方法,继承的子类要去实现
      run(distance: number): void {
        console.log(`奔跑速度为:${distance}`);
      }
    }
    
    const d = new Dog();
    d.eat("小白");
    d.run(100);
    

    二十三、TypeScript 泛型

    • < T >
    export {}; //确保和其他示例没有成员冲突
    
    
    // 不适用泛型
    function createNumbnerArray(length: number, value: number): number[] {
      const arr = Array<number>(length).fill(value);
      return arr;
    }
    
    function createStringArray(length: number, value: string): string[] {
      const arr = Array<string>(length).fill(value);
      return arr;
    }
    
    const res1 = createNumbnerArray(3, 100);
    const res2 = createStringArray(3, "100");
    
    
    // ·--------------------------------------------------------
    
    // 使用泛型
    function createArray<T>(length: number, value: T): T[] {
      const arr = Array<T>(length).fill(value);
      return arr;
    }
    
    const res3 = createArray<string>(3, "foo");
    
    console.log(res1);
    console.log(res2);
    console.log(res3);
    
    

    二十四、TypeScript 类型声明

    // 类型声明
    
    import { camelCase } from "lodash";
    import qs from "query-string";
    
    
    // declare function camelCase(input: string): string;
    const res = camelCase("hello typed");
    
    
    qs.parse('?key=fdfds&key2=fdfdfnmgf')
    
    // yarn add @types/lodash --dev   类型声明模块
    // yarn add query-string  //用来解析URL中的queryString字符串
    
    

    相关文章

      网友评论

        本文标题:TypeScript

        本文链接:https://www.haomeiwen.com/subject/lvdzdltx.html