字符串类型的打字稿 T[keyof T]
Typescript T[keyof T] of type string
我得到了一个 T
的数组,它有 string
类型的键。所以我想遍历数组中的所有条目和 trim 字符串。
错误:
Property 'trim' does not exist on type 'T[Extract<keyof T, string>]'
ifAlreadyExists<T>(
data: Array<T>,
key: Extract<keyof T, string>,
): boolean {
return (
data.filter(
(item) => {
const v = item[key];
return v.trim().toLowerCase()
}
).length === 0)
}
如何告诉 Typescript item[key]
将是字符串类型?
如 kaya3 所述,您的签名将 key
限制为字符串键,而不是具有字符串值的键。要执行后者,您可以引入一个类型变量 Key
(可以是任何键类型),并将数组元素限制为具有由 Key
表示的键的字符串值的对象(即 {[K in Key]: string}
):
ifAlreadyExists<Key extends PropertyKey>(
data: Array<{[K in Key]: string}>,
key: Key,
): boolean {
..
}
忽略过滤器中的布尔值与字符串 return 值,故意 不将 T
限制为 Record<PropertyKey, string>
.
使用 type-guard:
return (
data.filter(
(item) => {
const v = item[key];
if (typeof v === 'string') {
return v.trim().toLowerCase();
}
return 'something?';
}
).length === 0)
为了加分,您可能只想公开实现有效的密钥。
Only
生成一个类型,其中对于 T
的每个键,其对应的字段可分配给 U
.
type Only<T, U> = {
[K in keyof T]: T[K] extends U ? K : never
}[keyof T];
然后
ifAlreadyExists<T>(
data: Array<T>,
key: Only<T, string>, // only keys where values are string-like
): boolean {
...
}
而且 Book 形状中还有字符串以外的值。
type Book = {
id: string;
title: string;
isbn: number;
genre: 'fantasy' | 'horror'
};
const bookList: Array<Book> = [{ id: '222', title: 'Title 1', isbn: 1237681231, genre: 'fantasy' }];
this.ifAlreadyExists(bookList, "id"); // fine
this.ifAlreadyExists(bookList, "title"); // fine
this.ifAlreadyExists(bookList, "genre"); // fine
this.ifAlreadyExists(bookList, "isbn"); // Error! isbn is not string
我得到了一个 T
的数组,它有 string
类型的键。所以我想遍历数组中的所有条目和 trim 字符串。
错误:
Property 'trim' does not exist on type 'T[Extract<keyof T, string>]'
ifAlreadyExists<T>(
data: Array<T>,
key: Extract<keyof T, string>,
): boolean {
return (
data.filter(
(item) => {
const v = item[key];
return v.trim().toLowerCase()
}
).length === 0)
}
如何告诉 Typescript item[key]
将是字符串类型?
如 kaya3 所述,您的签名将 key
限制为字符串键,而不是具有字符串值的键。要执行后者,您可以引入一个类型变量 Key
(可以是任何键类型),并将数组元素限制为具有由 Key
表示的键的字符串值的对象(即 {[K in Key]: string}
):
ifAlreadyExists<Key extends PropertyKey>(
data: Array<{[K in Key]: string}>,
key: Key,
): boolean {
..
}
忽略过滤器中的布尔值与字符串 return 值,故意 不将 T
限制为 Record<PropertyKey, string>
.
使用 type-guard:
return (
data.filter(
(item) => {
const v = item[key];
if (typeof v === 'string') {
return v.trim().toLowerCase();
}
return 'something?';
}
).length === 0)
为了加分,您可能只想公开实现有效的密钥。
Only
生成一个类型,其中对于 T
的每个键,其对应的字段可分配给 U
.
type Only<T, U> = {
[K in keyof T]: T[K] extends U ? K : never
}[keyof T];
然后
ifAlreadyExists<T>(
data: Array<T>,
key: Only<T, string>, // only keys where values are string-like
): boolean {
...
}
而且 Book 形状中还有字符串以外的值。
type Book = {
id: string;
title: string;
isbn: number;
genre: 'fantasy' | 'horror'
};
const bookList: Array<Book> = [{ id: '222', title: 'Title 1', isbn: 1237681231, genre: 'fantasy' }];
this.ifAlreadyExists(bookList, "id"); // fine
this.ifAlreadyExists(bookList, "title"); // fine
this.ifAlreadyExists(bookList, "genre"); // fine
this.ifAlreadyExists(bookList, "isbn"); // Error! isbn is not string