如何在 Typescript 中将属性的类型设置为两个枚举的组合?
我有一个枚举:
enum EAlphabet = {
A = 'A',
B = 'B',
C = 'C',
D = 'D',
E = 'E',
F = 'F',
G = 'G',
H = 'H',
I = 'I',
J = 'J',
K = 'K',
L = 'L',
M = 'M',
N = 'N',
O = 'O',
P = 'P',
Q = 'Q',
R = 'R',
S = 'S',
T = 'T',
U = 'U',
V = 'V',
W = 'W',
X = 'X',
Y = 'Y',
Z = 'Z'
}
我有一个接口,我想给它的属性定义这样的类型:它可以是 'A'、'X'、'D' 中的一个,也可以是 'AA'、'JB'、'ZE' 中的一个,或者可以是 'ABC'、'ZJE' 中的一个。
我不确定该如何定义它,但可能是这样的?
interface foo {
bar: EAlphabet + EAlphabet? + EAlphabet? /* What to do here? */
}
答案#1
首先,在这种情况下,我更倾向于使用字面量联合而不是枚举,这样使用起来会非常方便。不幸的是,你无法在类型级别进行字符串拼接,但你可以将表示方式改为元组,并获得所需的类型安全性。
所以我的解决方案恰好包含字面量联合,但将其与枚举一起使用的区别实际上很小。
type EAlphabet = 'A' | 'B' | 'C' | 'D'; // literal union instead of enum
interface Foo {
bar: [EAlphabet] | [EAlphabet, EAlphabet] | [EAlphabet,EAlphabet,EAlphabet],
toString: () => string
}
const makeFoo = (chars: Foo['bar']): Foo => ({
bar: chars,
toString: function () {
return this.bar.join('');
}
});
const example = makeFoo(['A', 'B']); // only max three allowed, works
console.log(example.toString()) // outputs AB
const example2 = makeFoo(['A', 'B', 'C', 'D']); // error wrong size
const example3 = makeFoo(['A', '*', 'C']); // error wrong sign
解决方案的要点是 [EAlphabet] | [EAlphabet, EAlphabet] | [EAlphabet, EAlphabet, EAlphabet] 我们定义该类型是包含 1、2 或 3 个元素的元组,不允许更多。顺便说一下,如果允许任意大小,那么类型应该只是 EAlphabet[]。
同样重要的是,我们可以创建值构造函数 - makeFoo,它可以创建一个有效的类型值,如你所见,我还添加了方便的函数 toString,它允许我们获取字符串表示形式。所以即使我们在底层使用元组,我们也可以在任何时候将其转换为 string。
使用枚举实现这一点将是相同的,唯一的区别是我们需要传递枚举值而不是普通字面量:
const example = makeFoo([EAlphabet.A, EAlphabet.B]);
答案#2
枚举不是这样工作的,这也可能不是实现此目的的最佳方式。你可能需要将它定义为字符串,然后自己进行正则检查以查看它是否有 2-3 个字符等。
你可以(但你可能不应该)这样做。
// Array of EAlphabet with 2-3 Elements
export interface foo {
[0]: EAlphabet;
[1]: EAlphabet;
[2]?: EAlphabet;
}
let a: foo;
a = [EAlphabet.A, EAlphabet.X, EAlphabet.D];
请记住
a = ['A', 'B']
这样还是不行。
