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

为何TypeScript在检查string类型后,仍对string|number泛型的+运算报错?

TypeScript联合类型收窄疑问:已检查string类型后剩余分支为何报错?

我尝试实现一个支持两数相加或两字符串拼接的函数,代码如下:

type Add = <T extends string | number>(a: T, b: T) => T;

const add: Add = (a, b) => {
  if (typeof a === 'string' && typeof b === 'string') {
    return a + b;
  }

  return a + b; // 为什么这里报错?我们已经检查了一种类型,剩下的应该只有另一种类型了
}
const result = add('a', 'b');

tsconfig.json配置:

// tsconfig.json
"compilerOptions": {
    "target": "ESNext",
    "module": "ESNext",
    "moduleResolution": "bundler",
    "allowSyntheticDefaultImports": true,
    "esModuleInterop": true,
    "jsx": "preserve",
    "jsxImportSource": "solid-js",
    "allowJs": true,
    "noEmit": true,
    "strict": true,
    "noImplicitAny": true,
    "types": ["vinxi/types/client", "bun-types"],
    "isolatedModules": true,
    "paths": {
      "~/*": ["./src/*"]
    }
  }

问题解析

核心原因是泛型T的约束是string | number,但TypeScript无法将泛型参数本身收窄:

  • 泛型T在函数调用时确定,它可能被显式指定为string | number联合类型(比如add<string | number>(1, "2")),此时剩余分支中a和b的类型仍是string | number,a + b的结果会是string,但函数返回值要求是T(即string | number),类型不匹配。
  • 类型收窄只作用于具体值的类型,而非泛型参数的约束。你检查了a和b是string,但TypeScript无法推断出“此时T必然是number”——因为T本身可能包含两种类型。

解决方案

方案1:类型断言明确剩余类型

通过断言明确剩余分支中a和b为number,再断言返回值为T:

const add: Add = (a, b) => {
  if (typeof a === 'string' && typeof b === 'string') {
    return a + b;
  }
  return (a as number) + (b as number) as T;
}

方案2:使用函数重载

放弃泛型,用重载签名让TypeScript明确参数与返回值的对应关系:

function add(a: string, b: string): string;
function add(a: number, b: number): number;
function add(a: string | number, b: string | number) {
  if (typeof a === 'string' && typeof b === 'string') {
    return a + b;
  }
  return Number(a) + Number(b);
}

方案3:条件类型约束泛型

通过条件类型让返回值类型与T严格匹配:

type Add = <T extends string | number>(a: T, b: T) => T extends string ? string : number;

const add: Add = (a, b) => {
  if (typeof a === 'string' && typeof b === 'string') {
    return a + b;
  }
  return a + b as T;
}

内容的提问来源于stack exchange,提问作者Md. A. A. Apu

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.14 17:26:09