日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

TypeScript类型推论(Type Inference)

發(fā)布時間:2023/12/2 编程问答 40 豆豆
生活随笔 收集整理的這篇文章主要介紹了 TypeScript类型推论(Type Inference) 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

要完全理解類型推論需要完整理解類型上下文,并且理解TS對于是否可以使用類型推論是基于靜態(tài)分析完成的。
上下文類型應(yīng)用在許多地方。常見的例子包括函數(shù)調(diào)用的參數(shù)賦值的右手端位置類型斷言對象和數(shù)組的成員,和返回語句。上下文類型還充當(dāng)最佳公共類型中的候選類型。
TS中需要為每個JS名字規(guī)定類型,而名字出現(xiàn)在對應(yīng)的上下文中則會自動獲得類型,若沒有對應(yīng)的上下文,這個名字則會自動獲得類型any。

名字:通過聲明語句聲明的名字,例如var、let、const、function a() {}、class A {}、import A from ‘.a’、函數(shù)參數(shù)等,都會在JS環(huán)境中添加一個名字,而TS可以給這個名字指定類型。

在JS中名字的聲明是可以在上面提到的常見例子指定的位置,函數(shù)參數(shù)調(diào)用、賦值右手端位置、對象數(shù)組成員、返回語句。

函數(shù)調(diào)用的參數(shù)

interface Cb {(a: number): void; } interface Fn {(cb: Cb): void; }const fn: Fn = function (cb) {}fn(function (a) { // 這里a的類型是numberconsole.log(a + 1) })

因?yàn)閒n這個名字是類型Fn,而Fn類型的入?yún)⑹穷愋虲b,所以在fn使用匿名函數(shù)作為入?yún)⒄{(diào)用的時候TS可以知道這個匿名函數(shù)對應(yīng)的位置是類型Cb,換句話說匿名函數(shù)當(dāng)前的類型上下文是Cb。而Cb要求入?yún)⑹莕umber類型,所以推斷出匿名函數(shù)的參數(shù)a是number類型。

賦值的右手端位置

interface Cb {(a: number): void; }const fn: Cb = function (a) {console.log(a + 1) }

fn是類型Cb,因?yàn)镃b要求入?yún)⑹莕umber類型,所以TS推斷出對應(yīng)位置匿名函數(shù)的入?yún)⑹莕umber類型。

對象和數(shù)組的成員

interface Cb {(a: number): void; } interface Obj {fn: Cb } const obj: Obj = {fn: function (a) {console.log(a + 1)} }

obj是類型Obj,而Obj具有屬性fn是類型Cb。因?yàn)镃b要求入?yún)⑹莕umber類型,所以TS推斷出對象obj.fn右手端對應(yīng)位置匿名函數(shù)的入?yún)⑹莕umber類型。

返回語句

interface Cb {(a: number): void }interface Fn {(): Cb }const fn: Fn = function () {return (a) => {console.log(a + 1)} }

在這例子里,返回的匿名函數(shù)獲得類型上下文Cb,而Cb要求入?yún)⑹莕umber,所以匿名函數(shù)的入?yún)⒈煌茢喑鍪莕umber類型。

上面的幾種類型都可以認(rèn)為名字出現(xiàn)在了賦值的右手端,而被復(fù)制的名字可以給這個值提供對應(yīng)的類型上下文。

類型斷言

interface Fn {(a: number): void; }const fn = function (a) {console.log(a + 1); } as Fn;

在這里匿名函數(shù)賦值給變量fn而fn本身是沒有類型的,所以沒辦法推斷匿名函數(shù)的入?yún)的類型,但是我們使用類型給這個匿名函數(shù)指定了類型上下文Fn,讓TS具有了推算參數(shù)a的依據(jù),得出參數(shù)a是number類型。

小結(jié)

類型推斷起作用的條件是名字出現(xiàn)在對應(yīng)的上下文位置,而這個上下文可以通過賦值操作的左手端提供,也可以使用類型斷言直接提供。這樣TS可以根據(jù)對應(yīng)的類型推斷出對應(yīng)變量的類型。

一些意外

interface Fn {(a: number): void; }function fn(a) {}let a: Fn = fn

在這個例子里,TS無法推斷出函數(shù)fn的參數(shù)a是number類型,因?yàn)橘x值操作提供的類型上下文在右手端,而fn這個函數(shù)聲明的位置,并不是右手端。對應(yīng)的右手端位置并不是函數(shù)聲明,而是函數(shù)聲明的引用。所以TS無法靜態(tài)分析出fn中a的類型。
還有一個原因是fn的使用并不唯一,在這里我們將fn賦值給Fn類型的變量a,我們完全可以將它再賦值給Fn1類型的變量b,所以這種情況下fn中a的類型是由運(yùn)行時決定的,無法靜態(tài)分析出來。

interface Fn {(a: number): void; }function fn(a) {}let a: Fn = fninterface Fn1 {(a: number): void; }let b: Fn1 = fn

這里Fn1要求入?yún)的類型是string,所以fn的入?yún)既可能是number也可能是string,只有運(yùn)行這個函數(shù)的時候才能確定知道參數(shù)a是什么類型。所以在這個例子中a會自動獲得隱式類型any。

進(jìn)行如下修改:

interface Fn {(a: number): void; }let a: Fn = function fn(a) {}

在這里fn是一個表達(dá)式,并不會再當(dāng)前環(huán)境中新建一個名字fn,換句話說這個fn不會再用在別的地方,并且a這個名字直接出現(xiàn)在了右手端對應(yīng)位置,所以這個fn函數(shù)可以得到類型上下文Fn,從而推斷出參數(shù)a的類型是number。

總結(jié)

以上是生活随笔為你收集整理的TypeScript类型推论(Type Inference)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。