宣告檔案
什麼是宣告檔案?
讓我們來看看更通用的方式,有時也更方便的方式來宣告模組的類型:.flow
檔案。
有兩種可能的用例,視實作檔案是否存在而定。
在第一種情況下,模組的已匯出類型會宣告在宣告檔案 <FILENAME>.flow
中,該檔案位於與對應實作檔案 <FILENAME>
相同的目錄中。宣告檔案會完全覆蓋同置的實作。換句話說,Flow 會完全忽略 <FILENAME>
,而只讀取 <FILENAME>.flow
。
在第二種情況下,實作檔案完全不存在。<FILENAME>.flow
會被視為命名為 <FILENAME>
。
請注意,.flow
副檔名適用於 .js
檔案和 .json
檔案。對應的宣告檔案副檔名分別為 .js.flow
和 .json.flow
。
現在讓我們來看上面記錄的第一種情況的範例。假設我們在 src/LookBeforeYouLeap.js
檔案中有以下程式碼
import { isLeapYear } from "./Misc";
if (isLeapYear("2020")) console.log("Yay!");
假設 src/Misc.js
有 isLeapYear
的不相容實作
1export function isLeapYear(year: number): boolean {2 return year % 4 == 0; // yeah, this is approximate3}
如果我們現在建立宣告檔案 src/Misc.js.flow
,其中的宣告會用於取代 src/Misc.js
中的程式碼。假設我們在 src/Misc.js.flow
中有以下宣告。
注意:宣告檔案中宣告的語法與我們在 建立函式庫定義 章節中所見相同。
1declare export function isLeapYear(year: string): boolean;
你認為會發生什麼事?
沒錯,src/LookBeforeYouLeap.js
中的 isLeapYear
呼叫會進行類型檢查,因為宣告檔案中的 year
參數預期為 string
。
正如這個範例所示,宣告檔案必須謹慎撰寫:由程式設計師負責確保宣告正確無誤,否則可能會隱藏類型錯誤。
在一般程式碼中內嵌宣告
有時,在實作檔案的原始程式碼中內嵌宣告會很有用。
在以下範例中,假設你想要完成撰寫函式 fooList
,而不需要先模擬其相依性:函式 foo
會接收一個 number
並傳回一個 string
,而類別 List
則有一個 map
方法。你可以透過包含 List
和 foo
的宣告來執行此操作
1declare class List<T> {2 map<U>(f: (x: T) => U): List<U>;3}4declare function foo(n: number): string;5
6function fooList(ns: List<number>): List<string> {7 return ns.map(foo);8}
別忘了將宣告替換為適當的實作。