typescript type 分配條件類型示例詳解
引言
接上文type challenge(easy部分)關(guān)于分配條件類型,官方文檔描述地址。
之前看的時(shí)候沒真正理解,關(guān)于聯(lián)合類型的分配條件,官方文檔其實(shí)也沒有講得很明白,和翻譯無關(guān),英文文檔一樣很模糊,這些天做type challenge,發(fā)現(xiàn)有些題做出來的結(jié)果和預(yù)期不太一致,所以重新梳理這塊內(nèi)容。
先說結(jié)論
聯(lián)合類型什么時(shí)候會(huì)分配,必須符合4個(gè)條件(后面直接用條件1、條件2等代指下面條件):
首先,只分配extends前的內(nèi)容
- 無論這個(gè)extends是不是子斷言語句中的
- 例如
type Test<T> = 'b' extends 'b' ? (T extends 'b' ? true: false) : false;
, 其中的T extends 'b'
在子語句中,但事實(shí)上依舊是有效的
分配的內(nèi)容未做任何處理
type Test<T> = keyof T extends null ? never: false;
,T
被keyof
操作符處理了,因此不會(huì)分配- 官方文檔中,提到避免分配的方法
type ToArrayNonDist<Type> = [Type] extends [any] ? Type[] : never;
,能規(guī)避分配也是這個(gè)道理
分配內(nèi)容必須作為參數(shù)傳入
傳入時(shí)是聯(lián)合類型
題目解析
驗(yàn)證條件
條件1
type Test<T> = 'b' extends 'b' ? (T extends 'b' ? true: false) : false; Test<'a'| 'b'> // boolean
可見在子條件中的extends
也符合自動(dòng)分配,否則'a'|'b' extends 'b'
會(huì)返回false
,而不是true|false
條件2
發(fā)現(xiàn)這個(gè)問題是在DeepReadonly,題目地址
這一題一看看過去,直接寫出如下:
type DeepReadonly<T> = keyof T extends never ? T : {readonly [k in keyof T]: DeepReadonly<T[k]>};
但是發(fā)現(xiàn)對(duì)于測(cè)試用例X2
不生效
type X2 = { a: string } | { b: number }; DeepReadonly<X2> // { a: string } | { b: number }
仔細(xì)看,雖然X2是聯(lián)合類型,但keyof T extends never
顯然不符合前面說的條件2,因此不會(huì)自動(dòng)分配,而keyof ({ a: string } | { b: number })
值為never
。因此該題正確寫法如下:
type DeepReadonly<T> = { readonly [P in keyof T]: keyof T[P] extends never ? T[P] : DeepReadonly<T[P]>; };
條件3
顯然,普通使用extands
不會(huì)觸發(fā)自動(dòng)分配
type Test = 'a'|'b' extends 'a' ? true: false; // false
那么,假設(shè)傳入的參數(shù)是聯(lián)合類型,extends
前的對(duì)象也是聯(lián)合類型呢?
type Test<T> = 'b' extends 'b' ? (keyof T extends 'b' ? true: false) : false; type Result = Test<{a:1,b:string}|{a:2,b:number}> // false
這里,參數(shù)T
是聯(lián)合類型,但extends
前進(jìn)行了keyof
處理,但keyof {a:1,b:string}|{a:2,b:number}
結(jié)果為'a'|'b'
,依然是聯(lián)合類型,若這里進(jìn)行了自動(dòng)分配,結(jié)果應(yīng)是boolean
而非false
。
根據(jù)結(jié)果來看,這里并未進(jìn)行分配,這個(gè)例子同時(shí)違背了條件2和條件3
條件4
type Test<T> = 'a'|'b' extends 'b' ? T: false; Test<5> // false
條件4顯而易見,官方文檔上已經(jīng)說的很明確了。
不注意優(yōu)先級(jí)導(dǎo)致的錯(cuò)誤
在測(cè)試分配條件類型的規(guī)律時(shí),曾因?yàn)橐粭l用例卡了半天,用例如下:
type A = keyof null|undefined; // undefined type UndefinedExtendsNull = undefined extends null ? true: false; //false type Test<T> = keyof T extends null ? true: false; Test<null|undefined>; // true ?。。。?/pre>
此時(shí)已經(jīng)知道了,keyof T
會(huì)避免自動(dòng)分配,因此對(duì)于Test<null|undefined>
,可以寫成
keyof null|undefined extends null ? true : false; // 這里有個(gè)坑...
而keyof null|undefined
結(jié)果是undefined
,但是
type UndefinedExtendsNull = undefined extends null ? true: false; //false
結(jié)果是false
,同樣的式子,結(jié)果不一樣,一開始我以為是分配規(guī)律的理解有問題,但即使分配了,結(jié)果也應(yīng)該是true|false
,也就是boolean
,而不是true
。
后來發(fā)現(xiàn),type
是有優(yōu)先級(jí)的,且keyof
優(yōu)先級(jí)高于|
.
按理說keyof null|undefined
結(jié)果應(yīng)該是never
,之所以會(huì)顯示結(jié)果是undefined
,是因?yàn)閮?yōu)先級(jí)運(yùn)算:
keyof null|undefined -> (keyof null)|undefined -> never|undefined -> undefined
在實(shí)際寫類型的時(shí)候,要重點(diǎn)注意優(yōu)先級(jí)問題
以上就是typescript type 分配條件類型示例詳解的詳細(xì)內(nèi)容,更多關(guān)于typescript type分配條件類型的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
與ChatGPT結(jié)對(duì)編程實(shí)現(xiàn)代碼詳解
這篇文章主要為大家介紹了與ChatGPT結(jié)對(duì)編寫實(shí)現(xiàn)代碼詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-03-03微信小程序?qū)崙?zhàn)之運(yùn)維小項(xiàng)目
這篇文章主要介紹了微信小程序?qū)崙?zhàn)之運(yùn)維小項(xiàng)目,就是利用微信小程序?qū)崿F(xiàn)了一個(gè)類似138的功能,輸入IP就可以查看IP的詳細(xì)信心,有需要的朋友可以參考借鑒,下面來一起看看吧。2017-01-01TypeScript數(shù)據(jù)結(jié)構(gòu)鏈表結(jié)構(gòu)?LinkedList教程及面試
這篇文章主要為大家介紹了TypeScript數(shù)據(jù)結(jié)構(gòu)鏈表結(jié)構(gòu)?LinkedList教程及面試,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-02-02ThreeJS使用紋理貼圖創(chuàng)建一個(gè)我的世界草地方塊
這篇文章主要為大家介紹了ThreeJS使用紋理貼圖創(chuàng)建一個(gè)我的世界草地方塊的實(shí)現(xiàn)示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-06-06TypeScript開發(fā)HapiJS應(yīng)用詳解
這篇文章主要為大家介紹了TypeScript開發(fā)HapiJS應(yīng)用詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-08-08TypeScript之Generics泛型類型學(xué)習(xí)
這篇文章主要為大家介紹了TypeScript之Generics泛型類型學(xué)習(xí),有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-07-07Manipulation-TypeScript?DOM操作示例解析
這篇文章主要為大家介紹了DOM?Manipulation-TypeScript?DOM操作示例解析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-03-03