如何在typescript中使用多种类型的数组调用map函数

如何在typescript中使用多种类型的数组调用map函数,typescript,Typescript,我正在开发一个Typescript函数,它需要迭代类型为Employee[]| Guest[]的数组。问题是TypeScript发出错误TS2349:此表达式不可调用。。。具有签名,但没有一个签名彼此兼容。我希望能够迭代数组,并且在使用局部变量之前只需要使用类型保护,但情况似乎并非如此。是否有一种方法可以使用map函数而不必创建自定义类型?函数只需要迭代这两种类型,因此我希望将参数的类型定义保留为Employee[]| Guest[]。下面是一个简单的示例,people.map出现错误 inte

我正在开发一个Typescript函数,它需要迭代类型为
Employee[]| Guest[]
的数组。问题是TypeScript发出错误
TS2349:此表达式不可调用。。。具有签名,但没有一个签名彼此兼容
。我希望能够迭代数组,并且在使用局部变量之前只需要使用类型保护,但情况似乎并非如此。是否有一种方法可以使用
map
函数而不必创建自定义类型?函数只需要迭代这两种类型,因此我希望将参数的类型定义保留为
Employee[]| Guest[]
。下面是一个简单的示例,
people.map
出现错误

interface Employee {
  id: string;
  firstName: string;
}

interface Guest {
  firstName: string;
}

function getFirstNames(people: Employee[] | Guest[]): string[] {
  return people.map((x: Employee | Guest) => {
    return x.firstName;
  });
}

const employeeFirstNames = getFirstNames([
  {id: '1', firstName: 'Steve'},
  {id: '2', firstName: 'James'},
] as Employee[]);

const guestFirstNames = getFirstNames([
  {firstName: 'Mary'},
] as Guest[]);


键入数组作为
Employee
Guest
的联合

function getFirstNames(people: (Employee | Guest)[]): string[] {
  return people.map((x: Employee | Guest) => x.firstName);
}

键入数组作为
Employee
Guest
的联合

function getFirstNames(people: (Employee | Guest)[]): string[] {
  return people.map((x: Employee | Guest) => x.firstName);
}

我认为,在这种情况下,如果希望传递具有固定元素类型的数组,可以使用重载

function getFirstNames(people: Employee[]): string[];
function getFirstNames(people: Guest[]): string[];
function getFirstNames(people: (Employee | Guest)[]): string[] {
  return people.map((x: Employee | Guest) => {
    return x.firstName;
  });
}
在这种情况下,您不必担心公共接口,因此下面的混合类型将给出错误

const guestFirstNames = getFirstNames([
   { id: '1', firstName: 'Steve' },
  { firstName: 'Mary' }
]); // <-- No overload matches this call. Overload 1 of 2, '(people: Employee[]): string[]', gave the following error. Property 'id' is missing in type '{ firstName: string; }' but required in type 'Employee'. Overload 2 of 2, '(people: Guest[]): string[]', gave the following error. Type '{ id: string; firstName: string; }' is not assignable to type 'Guest'. Object literal may only specify known properties, and 'id' does not exist in type 'Guest'.
const guestFirstNames=getFirstNames([
{id:'1',名字:'Steve'},
{名字:'玛丽'}

]); // 我认为,在这种情况下,如果希望传递具有固定元素类型的数组,可以使用重载

function getFirstNames(people: Employee[]): string[];
function getFirstNames(people: Guest[]): string[];
function getFirstNames(people: (Employee | Guest)[]): string[] {
  return people.map((x: Employee | Guest) => {
    return x.firstName;
  });
}
在这种情况下,您不必担心公共接口,因此下面的混合类型将给出错误

const guestFirstNames = getFirstNames([
   { id: '1', firstName: 'Steve' },
  { firstName: 'Mary' }
]); // <-- No overload matches this call. Overload 1 of 2, '(people: Employee[]): string[]', gave the following error. Property 'id' is missing in type '{ firstName: string; }' but required in type 'Employee'. Overload 2 of 2, '(people: Guest[]): string[]', gave the following error. Type '{ id: string; firstName: string; }' is not assignable to type 'Guest'. Object literal may only specify known properties, and 'id' does not exist in type 'Guest'.
const guestFirstNames=getFirstNames([
{id:'1',名字:'Steve'},
{名字:'玛丽'}

]); // 这不允许在数组中混合类型吗?例如,我可以传递一个数组,该数组中同时包含
Employee
Guest
类型。它确实允许混合数组中的类型。我不认为你可以通过另一种方式实现。这是一个问题,因为函数只返回名字?如果数组包含混合类型,而函数不允许,那么期望的结果是什么?
(Employee | Guest)[
(Employee[]|Guest[]不同
,对吗?前者可以是一个包含混合类型元素的数组,但后者是同质的……我想使用您提供的解决方案并没有什么坏处。这只是从类型的角度考虑的问题。代码库中不应该有同时包含这两种类型的数组,但如果有一个函数接受这样的数组,则会提示它可以存在于某个地方。这不允许在数组中混合类型吗?例如,我可以传递一个数组,该数组中同时包含
Employee
Guest
类型。它确实允许在数组中混合类型。我认为您无法实现其他方法。这是一个问题,因为函数只返回firstNames?如果数组包含混合类型,而函数不允许它,那么期望的结果是什么?
(Employee | Guest)[
不同于
(Employee[]|Guest[]
,对吗?前者可以是一个包含混合类型元素的数组,但后者是同质的……我想使用您提供的解决方案并没有什么坏处。这只是从类型的角度考虑的问题。代码库中不应该有同时包含这两种类型的数组,但如果有一个函数接受这样的数组,则会提示它可以存在某个地方。@ABOS,为了防止
map
函数的细节/约束暴露给消费者,保持函数的签名不变然后将
map
行更改为
(人员身份(员工|客人)[])。map(…)
。因为
map
是函数的一个实现细节,不应该影响它的公共界面。如果使用
for
循环,我们可以保留
员工[]访客[]
type.Chuck,请参见answer@ABOS,为了防止
map
功能的细节/约束暴露给消费者,保持功能的签名不变,然后将
map
行更改为
(人员为(员工|客人)[])。map(…)
。因为
map
是函数的一个实现细节,不应该影响它的公共界面。如果使用
for
循环,我们可以保留
Employee[]| Guest[]
类型。Chuck,请查看答案