亚洲精品中文免费|亚洲日韩中文字幕制服|久久精品亚洲免费|一本之道久久免费

      
      

            <dl id="hur0q"><div id="hur0q"></div></dl>

                七爪源碼:自定義類型守衛(wèi)

                七爪源碼:自定義類型守衛(wèi)

                嘿,歡迎閱讀我們的 TypeScript Narrowing 系列的另一篇文章。 在這篇文章中,我將解釋:

              1. 類型謂詞
              2. 如何創(chuàng)建自己的警衛(wèi)
              3. 如何通過排除創(chuàng)建守衛(wèi)
              4. 這是我們系列的第三篇文章,如果你還沒有看過之前的文章,我強烈建議你去看看,它們?yōu)槭照峁┝藞詫嵉幕A。

                類型謂詞

                在上一篇文章中,我們探討了基本的類型保護運算符。 現(xiàn)在我想向你展示類型保護函數(shù)。

                例如,如果您需要檢查名為 value 的變量是否為字符串,則可以使用 typeof 運算符。 但你也可以做的是創(chuàng)建一個名為 isString() 的函數(shù),它接收一個參數(shù)并在給定參數(shù)是字符串時返回 true。

                const isString = (value: any): boolean => typeof value === ‘string’;

                還記得上一篇文章中的 formatErrorMessage() 函數(shù)嗎?

                const formatErrorMessage = ( value: null | undefined | string | Error | Warning): string => { const prefix = ‘Error: ‘; // If it’s falsy (null, undefined, empty string), return “Unknown” with the prefix if (!value) { return prefix + ‘Unknown’; } // If it’s a string, return the string with the prefix if (typeof value === ‘string’) { return prefix + value; } // If it’s a Warning, return the Warning.text with the prefix if (‘text’ in value) { return prefix + value.text; } // If it’s an Error, return the Error.message with the prefix if (value instanceof Error) { return prefix + value.message; } // We will never reach here throw new Error(`Invalid value type`);};interface Warning { text: string;}

                讓我們從中刪除 typeof 運算符并使用 isString() 代替。

                const formatErrorMessage = ( value: null | undefined | string | Error | Warning): string => { const prefix = ‘Error: ‘; // If it’s falsy (null, undefined, empty string), return “Unknown” with the prefix if (!value) { return prefix + ‘Unknown’; } // If it’s a string, return the string with the prefix if (isString(value)) { return prefix + value; } // If it’s a Warning, return the Warning.text with the prefix if (‘text’ in value) { return prefix + value.text; } // If it’s an Error, return the Error.message with the prefix if (value instanceof Error) { return prefix + value.message; } // We will never reach here throw new Error(`Invalid value type`);};interface Warning { text: string;}

                相同的代碼,我們只是在一個函數(shù)中隔離了守衛(wèi),對吧? 不,它壞了。 TypeScript 沒有將類型縮小為字符串,防護不起作用。

                事情是這樣的,isString() 返回一個布爾值,我們知道這個布爾值的含義。

                const isString = (value: any): boolean => typeof value === ‘string’;

                這意味著參數(shù)是一個字符串。 但是 TypeScript 不知道那個布爾值是什么意思,所以讓我們教它。

                與其說我們的函數(shù)返回一個布爾值,不如說我們的函數(shù)返回問題的答案:“這個參數(shù)是字符串嗎?”。

                鑒于我們的參數(shù)的名稱是 value,我們使用以下語法來做到這一點:value 是字符串。

                const isString = (value: any): value is string => typeof value === ‘string’;

                現(xiàn)在 TypeScript 知道 isString() 是一個類型保護并且我們的 formatErrorMessage() 函數(shù)可以正確編譯。

                我們的 isString() 函數(shù)的返回類型不再只是一個布爾值,它是一個“類型謂詞”。

                因此,要制作自定義類型保護,您只需定義一個返回類型謂詞的函數(shù)。

                所有類型謂詞都采用 { parameter } is { Type } 的形式。

                未知類型

                在我們繼續(xù)之前的快速提示:

                如果我們使用未知類型,我們的代碼會更安全,而不是在我們的自定義保護參數(shù)中使用類型 any。

                const isString = (value: unknown): value is string => typeof value === ‘string’;

                我制作了一個一分鐘的視頻來解釋任何和未知之間的區(qū)別,鏈接在參考資料中。

                自定義警衛(wèi)

                讓我們通過將 formatErrorMessage() 函數(shù)中的所有檢查轉換為自定義守衛(wèi)來鍛煉我們的知識。

                我們已經(jīng)有了字符串保護,現(xiàn)在我們需要警告、錯誤虛假類型的保護。

                錯誤防護

                Error 的保護非常簡單,我們只是將 instanceof 操作符檢查隔離在一個函數(shù)中。

                const isError = (value: unknown): value is Error => value instanceof Error;

                警戒衛(wèi)士

                但另一方面,Warning 守衛(wèi)并不是那么簡單。

                TypeScript 允許我們使用 in 運算符,因為我們的 value 參數(shù)可以是有限數(shù)量的類型,并且它們都是對象。

                const formatErrorMessage = ( value: null | undefined | string | Error | Warning): string => { const prefix = ‘Error: ‘; // If it’s falsy (null, undefined, empty string), return “Unknown” with the prefix if (!value) { return prefix + ‘Unknown’; } // If it’s a string, return the string with the prefix if (isString(value)) { return prefix + value; } // If it’s a Warning, return the Warning.text with the prefix if (‘text’ in value) { return prefix + value.text; } // If it’s an Error, return the Error.message with the prefix if (isError(value)) { return prefix + value.message; } // We will never reach here throw new Error(`Invalid value type`);};interface Warning { text: string;}

                但是如果我們創(chuàng)建一個函數(shù)并說我們的參數(shù)是未知的,那么它可以是任何東西。 包括原始類型,這會引發(fā)錯誤,因為我們只能在對象中使用 in 運算符。

                interface Warning { text: string;}const isWarning = (value: unknown): value is Warning => ‘text’ in value; // Compilation error

                解決方案是在使用 in 運算符之前確保我們的參數(shù)是一個有效的對象。 我們還需要確保它不為空。

                interface Warning { text: string;}const isWarning = (value: unknown): value is Warning => typeof value === ‘object’ && value !== null && ‘text’ in value;

                假守衛(wèi)

                對于虛假值守衛(wèi),我們首先需要定義一個類型,其值被認為是虛假的。

                type Falsy = false | 0 | -0 | 0n | ” | null | undefined;

                我在這里不包括 NaN,因為 TypeScript 中沒有 NaN 類型。

                type Falsy = false | 0 | -0 | 0n | ” | null | undefined | ~~NaN~~;

                NaN 的類型是數(shù)字,并非所有數(shù)字都是假的,所以這就是我們不處理 NaN 的原因。

                typeof NaN;//=> number

                有一個提議將 NaN 添加為一種類型——以及整數(shù)、浮點數(shù)和無窮大。 我認為這很好,擁有這些類型會很有幫助。

                // Proposaltype number = integer | float | NaN | Infinity;

                我將在參考文獻中留下該提案的鏈接。

                無論如何,現(xiàn)在我們有了 Falsy 類型,我們可以創(chuàng)建一個 falsy 值守衛(wèi)。

                請記住,如果一個值在轉換為布爾值時被認為是假的,那么它就是假的。 因此,要檢查我們的值是否為假,我們可以使用抽象相等來查看它是否被轉換為假。

                type Falsy = false | 0 | -0 | 0n | ” | null | undefined;const isFalsy = (value: unknown): value is Falsy => value == false;

                帶有自定義警衛(wèi)的 formatErrorMessage()

                就是這樣,我們現(xiàn)在擁有了 formatErrorMessage() 函數(shù)所需的所有自定義守衛(wèi)。

                // FUNCTIONconst formatErrorMessage = ( value: null | undefined | string | Error | Warning): string => { const prefix = ‘Error: ‘; // If it’s falsy (null, undefined, empty string), return “Unknown” with the prefix if (isFalsy(value)) { return prefix + ‘Unknown’; } // If it’s a string, return the string with the prefix if (isString(value)) { return prefix + value; } // If it’s a Warning, return the Warning.text with the prefix if (isWarning(value)) { return prefix + value.text; } // If it’s an Error, return the Error.message with the prefix if (isError(value)) { return prefix + value.message; } // We will never reach here throw new Error(`Invalid value type`);};// GUARDSconst isString = (value: unknown): value is string => typeof value === ‘string’;const isError = (value: unknown): value is Error => value instanceof Error;interface Warning { text: string;}const isWarning = (value: unknown): value is Warning => typeof value === ‘object’ && value !== null && ‘text’ in value;type Falsy = false | 0 | -0 | 0n | ” | null | undefined;const isFalsy = (value: unknown): value is Falsy => value == false;

                獎勵:通過排除縮小范圍

                在我們結束之前,我想向你展示一些東西。

                虛假值的列表是有限的,對嗎?

                1. `false`2. `0` `-0` `0n` representations of zero3. ““ `””` `”` empty string4. `null`5. `undefined`6. `NaN` not a number

                但另一方面,真實值是無限的。 所有不虛假的價值觀都是真實的。

                那么,如何為真實值創(chuàng)建類型保護呢?

                誠實守衛(wèi)

                訣竅是排除虛假類型。

                我們不是檢查我們的值是否為真,而是檢查它是否_不_假。

                type Truthy = Exclude;const isTruthy = (value: T): value is Truthy => value == true;// Testconst x = ‘abc’ as null | string | 0;if (isTruthy(x)) { x.trim(); // `x: string`}

                我經(jīng)常使用這個技巧,我們將在以后的文章中再次看到它。

                結論

                參考資料和其他鏈接如下。

                如果您還沒有,請在社交媒體上點贊、訂閱和關注我們。 這有助于我們成長,從而為您帶來更多免費內容。 這是雙贏的。

                鄭重聲明:本文內容及圖片均整理自互聯(lián)網(wǎng),不代表本站立場,版權歸原作者所有,如有侵權請聯(lián)系管理員(admin#wlmqw.com)刪除。
                用戶投稿
                上一篇 2022年6月12日 14:46
                下一篇 2022年6月12日 14:46

                相關推薦

                聯(lián)系我們

                聯(lián)系郵箱:admin#wlmqw.com
                工作時間:周一至周五,10:30-18:30,節(jié)假日休息