-
Notifications
You must be signed in to change notification settings - Fork 12.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Improved union/intersection type inference #5738
Conversation
@@ -6244,6 +6254,41 @@ namespace ts { | |||
} | |||
} | |||
|
|||
function typeIdenticalToSomeType(source: Type, target: UnionOrIntersectionType): boolean { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How about
return forEach(target.types, t => isTypeIdenticalTo(source, t) || undefined);
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Definitely an option, but not quite as efficient. I will keep what's there.
👍 |
} | ||
} | ||
if (modified) { | ||
return source.flags & TypeFlags.Union ? getUnionType(sourceTypes, /*noSubtypeReduction*/ true) : getIntersectionType(sourceTypes); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you break this into multiple lines?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use wordwrapping man.
Improved union/intersection type inference
@ahejlsberg You've got a little typo in your code example: function isUndefined<T>(x: Maybe<T>): x is void {
return x === undefined || x === null;
} |
@mariusschulz Yes indeed, thanks for catching that. |
Will this address issue mentioned in #3215 ? |
@ENikS No, the two are unrelated. |
@ahejlsberg Would inferring interface A { a: any; }
function test<T>(arg: A & T): T { ... }
let result = test({a: "", b: 10}); The type of |
@masaeedu We could potentially explore that, but it could get complex and would require type inference to manufacture new types, neither of which I'm crazy about. Specifically, in your example, we'd have to manufacture a new type |
This PR improves type inference involving source and target sides that are both union or intersection types. When inferring from a type S to a type T, if S and T are both union types or both intersection types, we first reduce S and T by removing constituents that are matched by a constituent in the other type. For example, when inferring from
string | string[]
tostring | T
, we reduce the types tostring[]
andT
, thus inferringstring[]
forT
.An example:
Fixes #2264.
Fixes #4212.
Fixes #5417.
Fixes #5456.