例举Typescript声明文件写法 您所在的位置:网站首页 typescript中的声明文件 例举Typescript声明文件写法

例举Typescript声明文件写法

2023-02-12 04:18| 来源: 网络整理| 查看: 265

刚开始写声明文件时,不知道如何下手。但是,随着反复的实验,以及参考一些公开的声明文件,发现写声明文件也不是那么难。只要熟悉Typescript,了解Typescript与javascript之间的异同,很容易就能够根据API写出对应的声明文件来

声明文件是以.d.td为后缀的文件,文件名称与javascript文件名称一致。声明文件主要是解决js文件在Typescript中的使用问题,有了声明文件,编译器就可以对引入的js库做类型检查,同时支持代码智能提示。

下面,就通过例子来讲解声明文件是如何编写的吧。

例1:关于方法的定义 API: getAccount(id) getInfo()

声明:

declare getAccount(id: number):void declare getInfo():any

方法只要在方法前加入declare即可暴露该方法。其次,如果方法有返回参数,可使用any,如果没有,可使用void,不写即为any,如果知道具体的类型,也可以填具体的类型。

例2:关于类型 2-1: 简单声明

常用的基本类型有 元组、数组、string、number、boolean,另外还有枚举

API: getName() 输出: "somenone"

声明:

declare getName():string //或 declare getName():any 2-2:多种类型 API: getExtraData(id) 输出: "somenone" 或者 1 或者 undefine

声明:

declare getExtraData(id:number): string|number|undefine //或 declare getExtraData(id:number):any //或 declare getExtraData(id:any):any

如果参数非必须,则可以这样定义

declare getExtraData(id?:number): string|number|undefine

任何类型都可以使用any替代,如果不知道是什么类型,或者不关心返回类型,或者返回类型太复杂,类型不止一种,这时候,通常用any替代是一个比较省事的方法。 当然,最好是越详细越好,这样可以方便编译器做类型检查以及代码提示,从而规范自己的代码

接下来的例子,类型同样可以使用any替代

2-3: 返回数据或参数为json对象

一般在声明文件中,返回的json数据可以单独定义成类型,基本类型也可以取别名。

declare type Name=string; declare type Info = { name: string }

举例:

API: # 方法 getAccount(id) # 输出 { "name":"someone", "age":12, "gender":true, "extra":{ "loginTome": 1 } }

声明:

declare type Result = { name: string, age: string, gender: true, extra: any } declare getAccount(id:number): Result

同样Result可以写成这样:

declare type ResultItem = { loginTome: number } declare type Result = { name: string, age: number, gender: true, extra: ResultItem }

如果图省事,可以这样定义:

declare type Result = { name: string, age: number, gender: true, extra:{ loginTome: number } }

也可以使用interface来定义:

declare interface Result{ name: string, age: number, gender: true, extra:{ loginTome: number } }

对于一些非必需的参数可以使用?,一些多类型的参数,可以使用|.

? = |undefine

declare type Result = { name: string, age: number, gender: true, extra?: { loginTome: number } } // 或 declare type Result = { name: string, age: number, gender: true, extra : { loginTome: number }|undefine }

由上述可以找到,声明文件的定义可以根据每个人的需求去定义,并不需要完全一致。甚至,如果方法太多,一些用不到的方法可以不声明。

同理,参数为json也是一样这样定义类型

例3:关于类

一般类使用class或者interface定义,如果类中有静态方法可熟悉 —— 即无须实例化对象即可使用的属性和方法,则需要将这些方法写到namespace中

其中声明文件最主要的一部分,就是类的声明。

例3-1:基本的类 var a = new Account(1); console.log(a.name) console.log(a.getExtra()) console.log(Account.TypeOfUser) Account.login(a.id) 输出: "someone" "{ "loginTime": 1 }" "USER"

声明:

declare class Account{ constructor(id: number); getExtra(): Account.ExtraData name:string id: number } declare namespace Account{ interface ExtraData{ loginTime: number } const TypeOfUser:string function login(id:number):any }

解析:

这里的ExtraData名字可以随意取,不要重名即可,也不一定放在Account的命名空间中,但是一般都放在命名空间中,这样就不会引起过多的全局变量,同时大大的减少重名的变量

例3-2 如果例3-1中的new去掉,该如何声明呢? var a = Account(1); console.log(a.name) ... declare function Account(id: number): Account; declare interface Account { getExtra(): Account.ExtraData name: string id: number } declare namespace Account { interface ExtraData { loginTime: number } const TypeOfUser: string function login(id: number): any } 例4: 方法的“重载”

声明文件允许出现多个相同名称的方法,在类和接口里面同样是允许这样做的

declare getExtraData(id?:number): any

那么前面提到的getExtraData可以有新的写法

declare getExtraData(id:number): any declare getExtraData(): any

这样,就可以很方便的区分可以传递不同数量参数的方法的情况

例5: 关于继承 API: getData(1) getResult(1) 输出: // getData { "id":1, "time": 0, "errCode": 0, "res":{ "name":"someone" } } // getResult { "id":1, "time": 0, "errCode": 0, "res":{ "age": 1 } }

跟例2-3一样,可以分别定义一个类型:

declare interface Data { id: number, time: number, errCode: number, res:{ name: string } } declare interface Result { id: number, time: number, errCode: number, res:{ age: number } }

但是这样,显然不是很好,因为可以看出来,Data和Result有很多相似的地方,所以应该是可以优化的,下面我就来介绍一下几种优化方法

方法1:一劳永逸的方法

把变化的部分类型定义为any,这样的话无论res如何变化,同一类型都可以用Base来作为返回结果(也可以是方法参数)的类型

declare interface Base { id: number, time: number, errCode: number, res: any } 方法2:兼容模式

使用|,可以不断的添加新的类型,不过在使用上会带来诸多不便,不建议使用

declare interface DataItem{ name: string } declare interface ResultItem{ age: number } declare interface Base { id: number, time: number, errCode: number, res: DataItem|ResultItem } 方法3:兼容模式2

在res内把所有可能的参数都加上,如果所有情况都出现,则无需加?,否则就要加?。这种方式也不太建议使用,不过在某些场合还是可以用到的。比如res中也有很多相同的字段,或者大部分都差不多。使用的时候带?的,需要判断是否为undefine。

declare interface Base { id: number, time: number, errCode: number, res: { name?: string age?: number } } 方法4:继承

这种方式感觉好像还麻烦了些,不过却是一个好的结构,没有出现重复的代码,也就意味着出现错误的几率会变小,同时类型越多,这种写法的优势就越明显,还是有一定的借鉴价值的。

interface Base { id: number, time: number, errCode: number } interface DataItem{ name: string } interface ResultItem{ age: number } declare interface Data extends Base { res: DataItem } declare interface Result extends Base { res: ResultItem } 方法5:继承 + 泛型

其中Item可以写上相同的属性,也可以是空接口。

利用泛型后,等于进一步优化了方法3。res是相同类型的都有的属性,但是其中结构又各有差异,所以用泛型是最好的选择。这个也是比较推荐的一种写法。

interface Item { } interface Base { id: number, time: number, errCode: number, res: Item } interface DataItem extends Item{ name: string } interface ResultItem extends Item{ age: number } declare interface Data extends Base {} declare interface Result extends Base {} 总结

写了这么多,可以知道,其实声明文件编写并不是那么严格,但是一个好的声明文件还是要越详细越好。如果是个人使用,方法和属性太多太杂的话,就可以考虑忽略掉那些不会用到的方法和属性,毕竟没必要花太多时间来编写声明文件。如果用到了,在添加上对应的声明即可。

同时,声明文件的编写,可以充分利用Typescript的特性,也要熟悉javascript的语法,这样就可以将js库的接口很好的对接上ts了。



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有