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

TypeScript如何定义需含指定键至少一个且无多余键的对象类型

TypeScript 符合要求的Person类型实现

需求梳理

我们需要定义的Person类型需要满足以下规则:

  • 可以只包含firstName属性
  • 可以只包含lastName属性
  • 可以同时包含firstName和lastName属性
  • 不允许包含任何其他额外属性
  • 不允许两个属性都为空(即空对象)

实现方案

方案1:联合类型实现(最简洁,兼容性好)

直接通过联合类型枚举所有合法的字段组合,TS会自动校验多余属性:

type Person = 
  | { firstName: string; lastName?: never }
  | { firstName?: never; lastName: string }
  | { firstName: string; lastName: string }

校验效果验证

合法输入不会报错:

// 全部合法
const p1: Person = { firstName: 'John' }
const p2: Person = { lastName: 'Wayne' }
const p3: Person = { firstName: 'John', lastName: 'Wayne' }

非法输入会触发TS报错:

// 报错:存在未定义的middleName属性
const p4: Person = { firstName: 'John', middleName: 'Bob', lastName: 'Wayne' }
// 报错:没有匹配的类型分支
const p5: Person = {}

方案2:通用禁止额外属性写法

如果后续需要扩展字段,不想手动枚举所有组合,可以用泛型工具实现:

// 禁止额外属性的工具类型
type NoExtraProps<T> = T & Record<Exclude<string, keyof T>, never>

// 定义Person的基础字段
type PersonBase = {
  firstName?: string
  lastName?: string
}

// 最终Person类型:禁止额外属性 + 至少存在一个字段
type Person = NoExtraProps<PersonBase> & (
  { firstName: string } | { lastName: string }
)

这个方案和方案1的校验效果完全一致,更适合字段较多的场景。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.26 02:24:03