From 7497d81eecd8a3a17f65154c0c657f9e7966fbb7 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Wed, 12 Oct 2016 14:12:32 -0700 Subject: [PATCH] Narrow string and number types in equality checks and switch cases --- src/compiler/checker.ts | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index a1a8ae0da5c..6555710137a 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -8791,6 +8791,10 @@ namespace ts { assumeTrue ? TypeFacts.EQUndefined : TypeFacts.NEUndefined; return getTypeWithFacts(type, facts); } + if (type.flags & TypeFlags.String && isTypeOfKind(valueType, TypeFlags.StringLiteral) || + type.flags & TypeFlags.Number && isTypeOfKind(valueType, TypeFlags.NumberLiteral)) { + return assumeTrue? valueType : type; + } if (type.flags & TypeFlags.NotUnionOrUnit) { return type; } @@ -8843,7 +8847,11 @@ namespace ts { const clauseTypes = switchTypes.slice(clauseStart, clauseEnd); const hasDefaultClause = clauseStart === clauseEnd || contains(clauseTypes, neverType); const discriminantType = getUnionType(clauseTypes); - const caseType = discriminantType.flags & TypeFlags.Never ? neverType : filterType(type, t => isTypeComparableTo(discriminantType, t)); + const caseType = + discriminantType.flags & TypeFlags.Never ? neverType : + type.flags & TypeFlags.String && isTypeOfKind(discriminantType, TypeFlags.StringLiteral) ? discriminantType : + type.flags & TypeFlags.Number && isTypeOfKind(discriminantType, TypeFlags.NumberLiteral) ? discriminantType : + filterType(type, t => isTypeComparableTo(discriminantType, t)); if (!hasDefaultClause) { return caseType; }