The below code outputs [ 5142, 5143 ]
, but I use any
as type.
let a = [{ _id: 5142 }, { _id: 5143 }];
a = a.map((e: any) => {
return e._id;
});
console.log(a);
Looking at the types I would think the correct type would be
a = a.map((e: { _id: number }) => {
but it fails.
I use VSCode. Can it tell me the correct type? Or is there a clever console.log(typeof)
trick?
CodePudding user response:
Fundamentally, assign the result of map
to something else, not to a
, since if you assign back to a
then a
has to be defined as number[] | { _id: number; }[]
(since it starts out being { _id: number; }[]
and then you're trying to turn it into number[]
).
If you assign it to something else, then you don't need to specify any types at all, TypeScript will infer them correctly:
const a = [{ _id: 5142 }, { _id: 5143 }];
const b = a.map((e) => {
return e._id;
});
console.log(b);
It's possible to reuse a
, but it's not clear why you'd want to. Here's what that would look like, but I don't recommend it:
let a: number[] | { _id: number; }[] = [{ _id: 5142 }, { _id: 5143 }];
a = a.map((e) => {
return e._id;
});
console.log(a);
TypeScript's flow analysis lets it see that when calling map
, a
is a { _id: number; }[]
, so we don't need a type guard. If it weren't obvious from context, you would:
function example(a: number[] | { _id: number; }[]) {
a = a.map((e) => {
return typeof e === "object" ? e._id : e; // Note the type guard
});
return a;
}
console.log(example([{ _id: 5142 }, { _id: 5143 }]));