javascript - Varför flaggar Typescript ett möjligt odefinierat värde vid kontroll av arraylängd med större än men inte med lika med?
Givet detta utsnitt av en React-komponent:
const AccountInformation = (props: { readonly accountData: AccountData | undefined | null }) => {
const hasMultipleAccounts: boolean = props.accountData?.customerAccounts?.length === 1 ? false : true
...
Varför klagar Typescript på att props.accountData?.customerAccounts?.length möjligen är undefined när jag kontrollerar om det är större än 0 (> 0) men felet försvinner när jag kontrollerar om det är lika med 1 (=== 1)?
Är detta ett fall där JS gör något konstigt med en odefinierad egenskap som tolkas som 0?
Att skriva det på det här sättet eliminerar felet, men jag försöker förstå beteendet.
const hasMultipleAccounts: boolean = props.accountData?.customerAccounts?.length ?? 0 > 1 ? : true : false
Svar #1
Om du vill använda length > 0 behöver du nullliknande sammanslagning:
const i: number | undefined = undefined;
if (i ?? 0 > 0) {
}
Svar #2
Enklare sagt, du frågar varför TypeScript klagar på det andra av dessa uttalanden:
console.log(undefined === 1); // false
console.log(undefined > 0);
// ^−−−− Object is possibly 'undefined'.(2532)
...eftersom alla egenskapsåtkomstoperationer med valfri kedjning i sig har undefined som ett av sina möjliga resultatvärden.
=== är mer generellt än >. === används för att se om typen av värdet hos operanderna matchar. Men > används antingen för att jämföra två nummer eller för att jämföra två strängar för relativ ”större”-het. TypeScript förhindrar också att blanda dessa två:
console.log("1" > 0);
// ^−−− Operator '>' cannot be applied to types 'string' and 'number'.(2365)
console.log(1 > "0"");
// ^−−− Operator '>' cannot be applied to types 'number' and 'string'.(2365)
I JavaScript är vi (ganska) vana vid implicit omvandling i dessa situationer, men TypeScripts uppgift är att tillämpa strikt typning, och därför tillåts implicit omvandling generellt inte. I JavaScript blir undefined > 0 till NaN > 0 vilket är false (liksom undefined <= 0). Men TypeScript ser det som det fel det sannolikt är och markerar det för dig.
(Länk till lekplatsen för allt ovanstående.)
