【问题标题】:Type definition for overlapping types重叠类型的类型定义
【发布时间】:2021-03-01 14:49:41
【问题描述】:

我想为一个函数创建类型定义,该函数接受两个不同类型的对象,但具有共同的键集:

function myFunc(left, right, keys) {
  // simplified:
  for (const key of keys) {
    console.log(key, left[key] === right[key])
  }

  return { left, right }
}

const left = {a: 1, b: 2}
const right = {b: 2, c: 3}
myFunc(left, right, ["b"])

这种方法有效,但会改变返回的 right 的类型,这在函数调用后的代码中会咬我:

function myFunc<
  Left,
  Keys extends keyof Left
>(
  left: Left,
  right: Pick<Left, Keys>,
  keys: Keys[],
): {
  left: Left
  right: Pick<Left, Keys>
} {
  // ...
}

我希望返回的类型相同:

function myFunc<
  Left,
  Right extends Pick<Left, Keys>,
  Keys extends keyof Left & keyof Right
>(
  left: Left,
  right: Right,
  keys: Keys[]
): { 
  left: Left
  right: Right
}  {
  // ...
}

但是,现在我收到Left[Keys]Right[Keys] 类型不重叠的抱怨。我没有完全理解。

任何提示或想法?

【问题讨论】:

标签: typescript typescript-generics typing


【解决方案1】:

一个奇怪的解决方案,但它似乎在简单的例子中工作。

Playground Link

function myFunc<
    L extends Pick<R, (keyof R & keyof L)>,
    R extends Pick<L, (keyof R & keyof L)>,
    K extends (keyof R & keyof L)>
    (left: L, right: R, keys: K[]): { left: L, right: R }
{
    for (const key of keys) {
        console.log(key, left[key] === right[key])
    }

    return { left, right }
}
const left = { a: 1, b: 2, c: 4 };
const right = { b: 2, c: 3, d: 5 };

// Work:
myFunc(left, right, [ 'b' ]);
myFunc(left, right, [ 'b', 'c' ]);

// Error: Type '<>' is not assignable to type '"b" | "c"'.
myFunc(left, right, [ 'a' ]);
myFunc(left, right, [ 'd' ]);
myFunc(left, right, [ 'z' ]);

但是,如果与重叠键对应的值的类型不匹配,它似乎确实存在一些问题。修复它可能是一个棘手的方法。

总的来说,如果可能,最好关闭=== 行的类型检查。

【讨论】:

    猜你喜欢
    • 2016-08-30
    • 2014-04-10
    • 1970-01-01
    • 2019-12-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多