You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

映射类型(Mapped Types):如何移除可选修饰符?

如何在TypeScript映射类型中移除可选修饰符

当然可以移除!你遇到的问题是因为默认情况下,TypeScript的映射类型会保留原属性的所有修饰符(包括可选性?)。要解决这个问题,只需要在映射的时候使用-?修饰符来显式移除可选标志。

解决方案1:直接使用-?修饰符

修改你的映射类型,在属性名后面加上-?,就可以把可选属性转为必填:

interface Foo {
  one?: string;
  two?: string;
}

type Foo2 = { [P in keyof Foo]-?: number; };
// 现在Foo2的类型是 { one: number; two: number; }

这里的-?是TypeScript映射类型的特殊语法,作用就是移除属性的可选修饰符。对应的,如果想给属性强制添加可选修饰符,可以用+?(不过默认映射已经会保留原属性的可选性,所以+?一般用在需要主动添加可选性的场景)。

解决方案2:使用内置工具类型Required<T>

TypeScript还提供了内置的Required<T>工具类型,它的核心作用就是将类型T的所有可选属性转为必填属性。你可以结合映射类型来使用它:

interface Foo {
  one?: string;
  two?: string;
}

// 先映射类型,再转为必填
type Foo2 = Required<{ [P in keyof Foo]: number; }>;

// 或者先把Foo转为必填,再映射类型(效果完全一致)
type Foo2 = { [P in keyof Required<Foo>]: number; };

两种写法最终得到的Foo2类型都是{ one: number; two: number; },选择哪种都可以,看你觉得哪种更直观。

验证效果

如果你用TypeScript编译器检查的话,现在Foo2的属性都是必填的了:

// 错误:缺少属性 'one' 和 'two'
const test: Foo2 = {};

// 正确
const valid: Foo2 = { one: 1, two: 2 };

内容的提问来源于stack exchange,提问作者NSjonas

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.22 07:45:44