模板字符串类型
类似于 JavaScript 中的模板字符串允许你将值插入到字符串中一样,TypeScript 中的模板字符串类型可以用来将其他类型插入到字符串类型中。
比如说我想创建一个 PngFile 类型,它需要是以 .png 结尾的字符串:
type PngFile = `${string}.png`;
这样的话,当我们定义一个 PngFile
类型的变量时,它必须以 .png 结尾:
let myImage: PngFile = "my-image.png";
当字符串与 PngFile 类型定义的模式不匹配时,TypeScript 将显示错误:
let myImage: PngFile = "my-image.jpg";
// ^^^^^^^
// ❗Type '"my-image.jpg"' is not assignable to type '`${string}.png`'.
这种技术有多种应用。我们可以确保字符串以特定前缀开头,例如要求路由以 / 开头:
type Route = `/${string}`;
const myRoute: Route = "/home";
const badRoute: Route = "home";
// ^^^^^^^^
// ❗ Type '"home"' is not assignable to type '`/${string}`'.
我们还可以确保字符串必须包含特定的子字符串,例如要求字符串必须包含 ? 才能被视为查询字符串:
type QueryString = `${string}?${string}`;
const myQueryString: QueryString = "search?query=hello";
const badQueryString: QueryString = "search";
// ^^^^^^^^^^^^^^
// ❗ Type '"search"' is not assignable to type '`${string}?${string}`'.
将模板字符串类型与联合类型组合
模板字符串类型还有一个常见的用法就是是与联合类型一起使用。通过将联合类型传递给模板字符串类型,可以生成一个代表联合类型所有可能组合的类型。
例如,假设我们有一组颜色,每种颜色的色调从 100 到 900 不等:
type ColorShade = 100 | 200 | 300 | 400 | 500 | 600 | 700 | 800 | 900;
type Color = "red" | "blue" | "green";
如果我们想组合所有可能的颜色和色调,可以使用模板字符串类型来生成一个新类型:
type ColorPalette = `${Color}-${ColorShade}`;
现在,ColorPalette 将表示颜色和色调的所有可能组合:
let color: ColorPalette = "red-500";
let badColor: ColorPalette = "red";
// ^^^^^^^^
// ❗Type '"red"' is not assignable to type '"red-100" | "red-200" | "red-300" | "red-400" | "red-500" | "red-600" | "red-700" | "red-800" | "red-900" | "blue-100" | "blue-200" | "blue-300" | "blue-400" | "blue-500" | "blue-600" | ... 11 more ... | "green-900"'.
这就是 27 种可能的组合(3 种颜色乘以 9 种色调)。
转换字符串类型
TypeScript 内置有几种用于转换字符串类型的内置实用程序类型。例如,"大写 "和 "小写 "可用于将字符串转换为大写或小写:
type UppercaseHello = Uppercase<"hello">; // type UppercaseHello is "HELLO"
type LowercaseHELLO = Lowercase<"HELLO">; // type LowercaseHELLO is "hello"
Capitalize 类型可用于将字符串的首字母大写:
type CapitalizeMatt = Capitalize<"matt">; // type CapitalizeMatt is "Matt"
Uncapitalize 类型可用于将字符串的首字母变为小写:
type UncapitalizePHD = Uncapitalize<"PHD">; // type UncapitalizePHD is "pHD"