-
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
Should unions and non-primitives be allowed for relational comparisons? #5156
Comments
Comparing strings and numbers is perfectly valid (if not a little wacky) JavaScript, isn't it? |
I mean, comparing anything is "valid javascript" (objects, arrays...), if not obviously meaningful. |
From an offline discussion, the consensus seems to be that the equality operations could keep something like this behavior, whereas other comparison operators should have their own rules. |
We should keep the idea of a new relationship on the backlog, i do not think we solved the underlying issue. closing this to avoid duplication though. |
This wasn't regarding the comparable relation, and even if it was, we've decided to use it for nullable types. |
I think that this is a bug and that |
why are relational operators valid for non-primitives in typescript? given that typescript is to make type checking pracical in javascript, I find it remarkable that things like the following do not give syntax errors:
|
further, why allow relational operations at all for non-primitives as they are useless and indicative of a coding or logic mistake?
|
after reading the original bug, maybe what I am posting is slightly different (a regression?) so maybe this should be a separate issue. edit: hmm, it seems like some object types can do relational operations correctly (such as Moment objects) so maybe I am wrong about this. would like to hear other opinions! |
I have been looking into this again - one direction that I've taken has been that two variables of type One question I ran into is whether this code should be allowd to be wrong: export function compareValues<T>(a: T, b: T): Comparison {
if (a === b) return Comparison.EqualTo;
if (a === undefined) return Comparison.LessThan;
if (b === undefined) return Comparison.GreaterThan;
return a < b ? Comparison.LessThan : Comparison.GreaterThan;
} Now, this function is "bad" in some sense - substituting In any case, let's assume that we want to fix this. Let's start writing two overloads: export function compareValues(a: number, b: number): Comparison;
export function compareValues(a: string, b: string): Comparison; Looks decent so far. Now what about an implementation signature? export function compareValues(a: ???, b: ???): Comparison {
if (a === b) return Comparison.EqualTo;
if (a === undefined) return Comparison.LessThan;
if (b === undefined) return Comparison.GreaterThan;
return a < b ? Comparison.LessThan : Comparison.GreaterThan;
} What can you put in for It's not entirely clear what to do here, but I think "good enough" might be the place to land. |
Seems we fixed this. Sometime things just work out! |
To quote 4.19.1 of the spec:
This has probably unintended consequences in the case of union types:
The question is: is this still desirable behavior?
@ahejlsberg @RyanCavanaugh @danquirk @mhegazy @JsonFreeman
The text was updated successfully, but these errors were encountered: