-
Notifications
You must be signed in to change notification settings - Fork 12.8k
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
future-proof type-checking of binary operators #23319
Comments
triage: P-backcompat-lang (1.0 beta) |
I've been working more on this. It turns out that my preferred solution (treat everything like a trait match) did not work because The idea is simple: for each binary operator This does cause some breakage, mostly when the RHS is an application of some generic trait method, e.g. Here is an example diff. I can tell you that the resulting code is definitely more readable to someone who has to come and read it for the first time (since that person was me, when making the change): #[inline]
fn is_infinite(self) -> bool {
- self == Float::infinity() || self == Float::neg_infinity()
+ self == f32::infinity() || self == f32::neg_infinity()
} There is one unresolved question. In my current branch, we don't do coercions for either side. This caused one broken change, where a I think I can restore the old coercion behavior, at the cost that trait dispatch viability is based only on the LHS. This will potentially impact future auto-ref fallback, because the decision of whether to autoref or not will be based solely on the LHS. |
Note: Presumably this will also break |
Example of code that fails to compile today but I think should compile (and compiles on my branch): http://is.gd/38Z70g |
After some discussion with @aturon, we decided that the better thing to do is revert to the previous approach (all traits, all the time) with some hacky code for SIMD. Basically using |
The current binary operator code assumed that if the LHS was a scalar (`i32` etc), then the RHS had to match. This is not true with multidispatch. This PR generalizes the existing code to (primarily) use the traits -- this also allows us to defer the precise type-checking when the types aren't fully known. The one caveat is unstable SIMD types, which don't fit in with the current traits -- in that case, the types must be known ahead of time. There is one semi-hacky bit in that during writeback, for builtin operators, if the types resolve to scalars (i32 etc) then we clear the method override. This is because we know what the semantics are and it is more efficient to generate the code directly. It also ensures that we can use these overloaded operators in constants and so forth. cc @japaric cc @aturon Fixes #23319 (and others).
The current binary operator code assumed that if the LHS was a scalar (`i32` etc), then the RHS had to match. This is not true with multidispatch. This PR generalizes the existing code to (primarily) use the traits -- this also allows us to defer the precise type-checking when the types aren't fully known. The one caveat is the unstable SIMD types, which don't fit in with the current traits -- in that case, the LHS type must be known to be SIMD ahead of time. There is one semi-hacky bit in that during writeback, for builtin operators, if the types resolve to scalars (i32 etc) then we clear the method override. This is because we know what the semantics are and it is more efficient to generate the code directly. It also ensures that we can use these overloaded operators in constants and so forth. cc @japaric cc @aturon Fixes #23319 (and others).
We need to invest a bit of energy to be sure that the way we handle binary operators is future-proof with possible plans:
@japaric has been doing some work on this in this PR #22993 and there is discussion there, including my preferred solution ;)
The text was updated successfully, but these errors were encountered: