美文网首页
Typescript 基本语法+ 新特性

Typescript 基本语法+ 新特性

作者: Simon_s | 来源:发表于2021-01-08 16:59 被阅读0次

    TypeScript :

    1、获取TypeScript

    $ npm install -g typescript
    
    1.1 编译TypeScript
    $ tsc helloworld.ts
    # helloworld.ts => helloworld.js
    

    2、TypeScript基础语法

    2.1 Boolean 类型
    let isDone: boolean  = false;
    
    2.2 Number 类型
    let count: number = 10;
    
    2.3 String 类型
    let name:   string = "zx"
    
    2.4 Array 类型
    let list: number[] = [1, 2, 3];
    let list: Array<number> = [1, 2, 3];(泛型语法)
    
    2.5 unknown 类型
    类型只能被赋值 any 类型 和 unknown 类型
    
    2.6 Tuple 类型(元组)
    let tupleType: [string, boolean];
    tupleType = ["Semlinker", true];
    
    2.7 Any 类型
    let notSure: any = 666;
    notSure = "Semlinker";
    notSure = false;
    在 TypeScript 中,任何类型都可以被归为 any 类型。这让 any 类型成为了类型系统的顶级类型(也被称作全局超级类型)。
    
    2.8 Enum 类型
    数字枚举:
    enum Direction {
        NORTH,
        SOUTH,
        EAST,
        WEST,
    }
    默认情况下,NORTH 的初始值为 0,其余的成员会从 1 开始自动增长
    
    字符串枚举:
    enum Direction {
      NORTH = "NORTH",
      SOUTH = "SOUTH",
      EAST = "EAST",
      WEST = "WEST",
    }       
          
    异构枚举:
    enum Enum {
      A,
      B,
      C = "C",
      D = "D",
      E = 8,
      F,
    }
       
    
    2.9 Void 类型
    某种程度上来说,void 类型像是与 any 类型相反,它表示没有任何类型。当一个函数没有返回值时,你通常会见到其返回值类型是 void:
    
    tips: 需要注意的是,声明一个 void 类型的变量没有什么作用,因为它的值只能为 undefined 或 null:
    
    2.10 Never 类型
    never 类型表示的是那些永不存在的值的类型。 
    例如,never 类型是那些总是会抛出异常或根本就不会有返回值的函数表达式或箭头函数表达式的返回值类型。
    
    在 TypeScript 中,可以利用 never 类型的特性来实现全面性检查,具体示例如下:
                type Foo = string | number;
          function controlFlowAnalysisWithNever(foo: Foo) {
              if (typeof foo === "string") {
                // 这里 foo 被收窄为 string 类型
              } else if (typeof foo === "number") {
                // 这里 foo 被收窄为 number 类型
              } else {
                // foo 在这里是 never
                const check: never = foo;
              }
          } 
    
    2.11 TypeScript 断言
    2.11.1尖括号 形式
    let someValue: any = "this is a string";
    let strLength: number = (<string>someValue).length;
    
    2.11.2 as语法
    let someValue: any  = "this is string"
    let strLength: number = (someValue as string).length
    
    2.12 类型守卫(类型保护)
    2.12.1 in 关键字
    interface Admin {
        name:   string;
        privileges: string[];
    }
    
    interface Employee {
         name: string;
         startDate: Date;
    }
    
    type UnknownEmployee = Employee | Admin
    
    function printEmployeeInformation( emp: UnknownEmployee) {
        console.log( "Name:" + emp.name)
        if("privileges" in emp) {
            console.log("Privileges" + emp.privileges);
        }
        if("startDate" in emp) {
            console.log("Start Date" + epm.startDate)
        } 
    }
    
    2.12.2typeof 关键字
    function padLeft( value: string, padding: string | number) {
        if(typeof padding === "number"){
            return Array(padding + 1).join("") +value;
        }
        if(typeof padding === "string") {
            return padding + value
        }
        throw new Error(`Expected string or number, got '${padding}'.`)
    }
    
    注释:typeof类型保护只支出两种形式;typeof v === "typename" 和 
    typeof v !=="typename", typename 必须是 "string","number","boolean"或 "symbol"; 但是 typeof  不会阻止你与其他字符串比较; 语言不会把那些表达式当成类型保护
    
    2.12.3 instanceof关键字
    interface Padder {
        getPadderString() : string;
    }
    class SpaceRepeatingPadder implements Padder {
         constructor(private numSpaces: number ) {}
         getPadderString() {
                return Array(this.numSpace + 1 ).join("");
         }
    }
    
    class StringPadder implements Padder {
            constructor(private value:string ) {}
            getPaddingString(){
                return this value;
            }
    }
    
    let padder : Padder = new SpaceRepeatingPadder(6);
    if(padder instanceof SpaceRepeatingPadder) {
        // padder的类型收窄为:"SpaceRepeatingPadder"
    }
    
    2.12.4 自定义类型保护的类型谓词
    function isNumber (x :any): x is number {
        return trpeof x === "number"
    }
    function isString( x :any ): x is string {
        return typeof x === "string"
    }
    

    3.vue3.0 新特性语法

    3.1 setup函数
    一、生命周期函数 beforeCreate 和 Created 两个钩子函数之间的函数; 在setup 函数中是无法访问到 data 以及 medthods 的数据以及方法
    二、setup函数是 Composition API(组合API)的入口
    三、在setup方法中。由于还没有执行 Created周期 无法访问到this
    四、setup函数只能是同步的不能是异步的
    五、setup 函数定义的方法以及变量最后必须 return 出去 不然模板中是无法使用的
    export default {
      setup(props, context) {
        context.attrs, 
        context.slots,
        context.parent, 
        context.root, 
        context.emit
      }
    };
    
    3.2 Reactive、Ref、toRef、IsRef

    reactive 和 ref 均为 数据响应式监听 方式
    ref 函数传入一个值作为参数,返回一个基于该值的响应式ref对象 该对象一旦被访问或改变,如下 修改 count.value 的值 就可以触发重新渲染显示最新的值;但是ref虽然写法简单,但是只能监听一些简单的数字、字符串、布尔之类的简单类型;

     eg:
     export default {
        setup () {
          const count = ref(0)
          const state = reactive({
            reactiveField: 0,
            a: [
              {
                a:1
              }
            ]
          })
          const addRef = () => {
            count.value++
          }
          const addReactive = () =>{
            state.reactiveField++
          }
          const addA = () => {
            state.a[0].a++
          }
          return {
            count,
            ...toRefs(state),
            addA,
            addRef,
            addReactive
          }
        }
      } 
    

    一、toRef 将响应式对象变为普通的对象 ...toRef(data) 在模板中即可使用数据 无需增加 例: data.value
    二、reactive 响应式数据 readonly 和 reactive 是互斥的数据结构

    3.3 defineComponent

    defineComponent函数,只是对setup函数进行封装,返回options的对象;
    defineComponent最重要的是:在TypeScript下,给予了组件 正确的参数类型推断 。

    export function defineComponent(options: unknown) {
        return isFunction(options) ? { setup: options } : options
    }
    
    3.4 watchEffect 监听

    接收一个函数,当依赖改变时,重新调用该函数

    const count  = ref(0)
    watchEffect(()=> console.log(count.value))
    setTimeout(()=>{
        count.value ++
    },1000)
    

    watchEffect()在setup()或生命周期钩子中被调用时,监听就始终存在该组件的生命周期中,直到组件unmount.另一种卸载监听的情况是,watchEffect()返回一个stop handler,调用该handler即可停止监听。

    const stop = watchEffect(()=>{
          //todo
    })
    stop()
    

    当向后台获取数据时,watchEffect 接受async回调函数

    const data = ref(null)
    watchEffect( async ()=> {
            data.value = await fetchData(props.id)
    })
    

    在 update 函数也有 watch Effect 用户定义的watchEffect 会在组件中update 之后再去调用

    <template>
      <div>{{ count }}</div>
    </template>
    
    <script>
      export default {
        setup() {
          const count = ref(0)
    
          watchEffect(() => {
            console.log(count.value)
          })
    
          return {
            count
          }
        }
      }
    </script>
    

    上述代码,第一轮会同步打印count.value(在onmount生命周期前); 当count发生改变时,先执行组件更新,然后再去log

    如果希望 watchEffect 中的回调函数 第一次执行,放在onmount 后

    onMounted(()=>{
            watchEffect(()=>{
                    //to do something
            })
    })
    

    如果想让 watchEffect() 调用发生在组件update前,或re-run同步,需要传递一个带有flush属性 ( 默认值为post ) 的option对象。

    watchEffect(()=>{
        //....
    },{
        flush: 'sync'
    })
    
    3.5 watch

    watch:watch( source, cb, [options] )
    参数说明:

    • source:可以是表达式或函数,用于指定监听的依赖对象
    • cb:依赖对象变化后执行的回调函数
    • options:可参数,可以配置的属性有 immediate(立即触发回调函数)、deep(深度监听

    当监听 ref 类型时

    
    <script>
    import {ref, watch} from 'vue'
    export default {
        setup() { 
            const state = ref(0)
    
            watch(state, (newValue, oldValue) => {
              console.log(`原值为${oldValue}`)
              console.log(`新值为${newValue}`)
              /* 1秒后打印结果:
                      原值为0
                      新值为1
              */
            })
    
            // 1秒后将state值+1
            setTimeout(() => {
              state.value ++
            }, 1000)
        }
    }
    </script>
    

    当监听 reactive 类型时

    <script>
    import {reactive, watch} from 'vue'
    export default {
        setup() { 
            const state = reactive({count: 0})
    
            watch(() => state.count, (newValue, oldValue) => {
              console.log(`原值为${oldValue}`)
              console.log(`新值为${newValue}`)
              /* 1秒后打印结果:
                      原值为0
                      新值为1
              */
            })
    
            // 1秒后将state.count的值+1
            setTimeout(() => {
              state.count ++
            }, 1000)
        }
    }
    </script>
    

    同事监听多个值(数组形式展示)

    <script>
    import {reactive, watch} from 'vue'
    export default {
        setup() { 
            const state = reactive({ count: 0, name: 'zs' })
    
             watch(
                [() => state.count, () => state.name], 
                ([newCount, newName], [oldvCount, oldvName]) => {
                  console.log(oldvCount) // 旧的 count 值
                  console.log(newCount) // 新的 count 值
                  console.log(oldName) // 旧的 name 值
                  console.log(newvName) // 新的 name 值
                }
              )
    
              setTimeout(() => {
                state.count ++
                state.name = 'ls'
              }, 1000)
        }
    }
    </script>
    
    3.6 onRenderTracked onRenderTriggered 新钩子

    除了2.x生命周期等效项之外,3.0Composition API还提供了以下调试挂钩

    • onRenderTracked
    • onRenderTriggered
      两个钩子都收到DebuggerEvent类似于onTrackonTrigger观察者的选项
    export default {
      onRenderTriggered(e) {
        debugger
        // inspect which dependency is causing the component to re-render
      }
    }
    

    先更新到这里! 持续更新~~~

    相关文章

      网友评论

          本文标题:Typescript 基本语法+ 新特性

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