目前是否有将两个或多个字符串文字类型连接到 TypeScript 中的单个字符串文字类型的方法?

IT技术 javascript string typescript function types
2021-02-09 13:14:09

首先,让我说清楚我正在寻找的不是联合类型,而是直接连接,即"Hel" + "lo" = "Hello"字符串文字类型

本质上,我有一个函数,它接受两个字符串文字 anamespace和 a name,并将它们与中间的 / 组合作为输出,但我无法找到一种方法使输出成为字符串文字而不是通用字符串。

我需要它是一个字符串文字,因为输出将用作对象的键。

我试过输入intersections( &), +,.concat()

function makeKey<NS extends string, N extends string>(namespace: NS, name: N) {
    return namespace + '/' + name; // <- want this to be `NS + / + N` = `NS/N`
}
// I want this to return a string literal rather than a generic string

const objKey = makeKey('admin', 'home')
// I want typeof objKey to be a string literal: `"admin/home"`, not a generic `string`

typeofobjKey是一个泛型,string但我希望它是一个string literal "admin/home"

3个回答

TS4.1+ 答案:

您现在可以使用模板文字类型来执行此操作:

function makeKey<NS extends string, N extends string>(namespace: NS, name: N) {
    return namespace + '/' + name as `${NS}/${N}`
}

const objKey = makeKey('admin', 'home');
// const objKey: "admin/home"

游乐场链接


TS4.1 之前的答案:

不幸的是,答案是否定的在 GitHub 中提交了几个功能建议,如果实施,可能会给你这样的功能(microsoft/TypeScript#12754在映射类型期间增加键,或microsoft/TypeScript#6579通过正则表达式操作字符串类型)但我没有认为他们正在积极工作。无论如何,我在路线图中没有看到任何关于它的内容。如果您真的希望看到这种情况发生,您可能想要访问其中一个 GitHub 问题并给他们一个 👍 或描述您的用例(如果它特别引人注目)。但我不会屏住呼吸。对不起!

谢谢@jcalz!我继续在我的用例中对其中一个线程发表评论。
2021-03-15 13:14:09
我不知道这是一回事。很酷,谢谢。
2021-04-01 13:14:09

一旦模板字符串类型将被释放(看起来像typescript4.1),这将是可能的

function makeKey<NS extends string, N extends string>(namespace: NS, name: N) {
    return (namespace + '/' + name) as `${NS}/${N}`;
}

const objKey = makeKey('admin', 'home') // objKey is of type 'admin/home'

操场


模板字符串类型是模板字符串表达式的类型空间等价物。类似于模板字符串表达式,模板字符串类型括在反引号定界符,并且可以包含以下形式的占位符${T},其中T是一类是分配给stringnumberboolean,或bigint模板字符串类型提供连接文字字符串、将非字符串原始类型的文字转换为其字符串表示形式以及更改字符串文字的大小写或大小写的能力。此外,通过类型推断,模板字符串类型提供了一种简单的字符串模式匹配和分解形式。

一些例子:

type EventName<T extends string> = `${T}Changed`;
type Concat<S1 extends string, S2 extends string> = `${S1}${S2}`;
type T0 = EventName<'foo'>;  // 'fooChanged'
type T1 = EventName<'foo' | 'bar' | 'baz'>;  // 'fooChanged' | 'barChanged' | 'bazChanged'
type T2 = Concat<'Hello', 'World'>;  // 'HelloWorld'
type T3 = `${'top' | 'bottom'}-${'left' | 'right'}`;  // 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right'

更多细节和例子在这里

它对as我有用,typescript 3.7.2,使用模板文字来连接和关键字来指定我的函数的输出类型。

const addSuffixToMyStringLiteral =
    (m: MyStringLiteral, suffix: string) => `${m}${suffix}` as MyStringLiteral;

我不知道它是否是typescript的新功能。

响应类型是 MyStringLiteral。OP 预期,例如literalexamplesuffix。
2021-03-19 13:14:09