在 TypeScript 中建立類似於 Keyof 的自定義 Valueof 來返回屬性值型別的聯合
-
在 TypeScript 中使用
valueof返回屬性值型別的聯合 -
在 TypeScript 中使用
keyof和typeof返回屬性值型別的聯合 - 使用 TypeScript 中的單個鍵獲取屬性值型別
- 在 TypeScript 中使用泛型在編譯時檢查鍵值
在本教程中,我們將學習可以用來返回構成屬性或物件的型別的不同方法。
我們可以使用三種方法來實現此功能。其中一種方法利用泛型建立名為 valueof 的自定義型別,該型別返回屬性的所有聯合型別。
第二種方法使用 keyof 和 typeof 型別返回屬性的所有聯合型別。第三種方法根據需要使用單獨的鍵返回單一型別。
我們還將學習在編譯時限制鍵值條目,如果它們不是同一型別,則通過利用泛型和索引訪問型別。
在 TypeScript 中使用 valueof 返回屬性值型別的聯合
轉到 Visual Studio Code 並建立一個名為 typescript-types 的資料夾或使用你喜歡的任何名稱。在資料夾下建立一個名為 value-types-using-valueof.ts 的檔案。
將以下程式碼複製並貼上到 value-types-using-valueof.ts 檔案中。
type ValueOf<T> = T[keyof T];
type Customer = {
firstName: string,
lastName: string,
doB: Date,
}
type ValueOfCustomer = ValueOf<Customer>
let customer: Customer ={
firstName: 'john',
lastName: 'doe',
doB: new Date(2022,12,6),
}
function logDetails(customerInfo: ValueOfCustomer){
console.log(customerInfo)
}
logDetails(customer.firstName)
logDetails(customer.lastName)
logDetails(customer.doB)
logDetails(500)// Error - The union does not include type number
首先,我們定義一個泛型型別 ValueOf<T> 並將其分配給 T[keyof T]。T 表示任何型別都可以傳遞給 ValueOf,無論是屬性還是物件。
keyof 返回屬於傳遞型別的所有鍵型別的聯合。
我們建立了包含屬性 firstName、lastName 和 doB 的 Customer 物件。前兩個屬性是字串型別,最後一個屬性是日期型別。
接下來,我們通過將 Customer 傳遞給 ValueOf<Customer> 泛型型別,建立了一個名為 ValueOfCustomer 的型別。ValueOfCustomer 是我們的新型別,由 Customer 物件中所有關鍵時間的聯合組成。
這意味著 ValueOfCustomer 只能接受型別為字串和日期的值。
為了驗證,我們建立了一個名為 logDetails() 的方法,該方法接受 ValueOfCustomer 型別的引數,並使用它記錄 Customer 的 firstName、lastName 和 doB。
請注意,如果我們嘗試在方法中傳遞非字串或日期型別的值,例如數字,我們將收到錯誤,因為方法引數只接受字串或數字。
在 TypeScript 中使用 keyof 和 typeof 返回屬性值型別的聯合
在同一資料夾中,建立一個名為 value-types-using-keyof-and-typeof.ts 的檔案。將以下程式碼複製並貼上到檔案中。
type Customer = {
firstName: string,
lastName: string,
doB: Date,
}
const customer: Customer ={
firstName: 'john',
lastName: 'doe',
doB: new Date(2022,12,6),
} as const
type customertypes = typeof customer[keyof Customer]
function getCustomerInfo(theCustomerTypes: customertypes){
console.log(theCustomerTypes)
}
getCustomerInfo(customer.firstName)
getCustomerInfo(customer.lastName)
getCustomerInfo(customer.doB)
getCustomerInfo(234)//Error - The union does not include type number
在上面的程式碼中,我們定義了包含屬性 firstName、lastName 和 doB 的 Customer 型別。前兩個屬性是字串型別,最後一個屬性是日期型別。
Customer 物件使用物件中每個屬性的具體值進行初始化。名為 customertypes 的型別已建立並分配給 typeof customer[keyof customer]。
在最後一個例子中,我們提到 keyof 返回所有鍵型別的聯合。這已經應用到我們的 Customer 物件上來做同樣的事情。
typeof 將返回從 Customer 物件獲取的所有型別,這是在 keyof 的幫助下實現的,如程式碼所示。
為了驗證這一點,我們建立了一個名為 getCustomerInfo() 的方法,該方法接受 customertypes 型別的引數,並使用它來記錄 Customer 物件的值。
請注意,如果我們嘗試傳遞非字串或日期型別的值(例如數字),則在該方法中,我們將收到錯誤訊息,因為新型別不包含型別編號。
使用 TypeScript 中的單個鍵獲取屬性值型別
在上面的兩個示例中,我們已經介紹瞭如何檢索所有值型別的聯合,但在某些情況下,你可能只對一種型別的物件感興趣。
在此示例中,你將學習如何使用單個鍵檢索物件的單個值型別。
在同一資料夾下,建立一個名為 individual-keys.ts 的檔案。將以下程式碼複製並貼上到檔案中。
type Customer = {
firstName: string,
lastName: string,
doB: Date,
}
type date = Customer['doB']
function getDateOfBirth(doB: date): Date{
return doB;
}
let customer: Customer ={
firstName: 'john',
lastName: 'doe',
doB: new Date(2022,12,6),
}
getDateOfBirth(customer.doB)
getDateOfBirth(123)//Error - Method accepts a single parameter of type date
在此示例中,我們重用了與前面示例中相同的客戶定義。日期型別是通過使用 Customer['doB'] 引用客戶定義中的 doB 鍵建立的。
這意味著新的 date 型別是 Date 型別。getDateOfBirth() 包含一個 date 型別的引數,並已用於驗證是否只能將日期型別傳遞給它,如程式碼所示。
如果我們嘗試傳遞一個不是 date 型別的值,例如一個數字,我們會得到一個錯誤,因為引數被限制為單一型別。
在 TypeScript 中使用泛型在編譯時檢查鍵值
如前面的示例所示,物件由鍵和值組成。有時我們可能會面臨根據其鍵更改物件值的要求。
在本教程中,我們將學習確保在編譯時檢查我們傳遞的值,以確保它們與鍵的型別相同。
在同一資料夾下建立一個名為 key-value-checking.ts 的檔案。將以下程式碼複製並貼上到檔案中。
type Shipment = {
containerItems: string,
containerSerial: string
shipmentDate: Date
}
declare function updateShipment<K extends keyof Shipment>(key: K, value: Shipment[K]): void;
updateShipment('containerItems','flowers')
updateShipment('containerSerial','def456');
updateShipment('shipmentDate',new Date(2018,3,14))
updateShipment('shipmentDate',1337)// Error- Shipment object does not contain type number
在上面的程式碼中,我們定義了一個名為 Shipment 的物件,其中包含引數 containerItems、containerSerial 和 shipmentDate。
前兩個屬性是字串型別,最後一個屬性是日期型別。我們定義了一個名為 updateShipment() 的通用方法。
updateShipment() 方法接受兩個引數,其中一個是鍵,第二個是 Shipment 物件的值。
鍵必須是任何型別的 Shipment 物件鍵,並使用尖括號引數中的 <K extends keyof Shipment> 進行檢查。
由於我們有鍵 K,我們可以通過使用 Shipment[K] 索引 Shipment 物件的鍵來限制傳遞給該鍵的值。使用此定義,我們為鍵輸入的每個值都必須與鍵的型別相同。
請注意,如果你嘗試傳遞未在 Shipment 物件中定義的值,例如數字,編譯器會標記問題。
David is a back end developer with a major in computer science. He loves to solve problems using technology, learning new things, and making new friends. David is currently a technical writer who enjoys making hard concepts easier for other developers to understand and his work has been published on multiple sites.
LinkedIn GitHub