-
Notifications
You must be signed in to change notification settings - Fork 13k
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
Changing the type of self in methods doesn't work #27941
Comments
Explicitly specifying the type of self using the syntax The explicit type syntax will probably be deprecated at some point. |
/cc @rust-lang/lang , what do you think? Should we explain this more, or leave it as is? |
@eefriedman On the contrary, One constraint we could put on it is that
That implies you could have, e.g. |
compatibility with the trait? I would prefer to store explicit Self explicitly and use the normal check_method code. If we want decent performance, requiring the method to appear in the autoderef loop would be nice (so do the autoderef loop in a probe, gather all methods, then sort them by priority and find the first matching one). |
@arielb1 Wording was unclear, I edited that bit. |
untagging docs and tagging with lang until @rust-lang/lang tells me what they want here |
Triage: over a year later, nothing has happened with more exotic So: closing this ticket, in my mind, involves fixing the diagnostic to say "or Box". |
(FWIW, I think we really want, at minimum, |
Nominating for lang team discussion. I assume this needs an RFC? Or perhaps there already was one, just not yet implemented. |
I think an RFC would be a good idea, just so we spend some time thinking carefully about the cases. In particular, it's important to work out how this interacts with trait objects. |
Some notes from the @rust-lang/lang meeting:
If someone is interested in pursuing it, we'd be happy to work with them (feel free to ping me), but it's not the highest priority at the moment. |
I think this issue has just gained some fire for prioritization with the recent introduction of generators and async/await. See https://github.com/alexcrichton/futures-await/tree/e09c87c7aa796bf6e5b6d8d45d6cba2078d12210#borrowing for a motivating example for |
@nikomatsakis @arielb1 Can we consider this for the impl period? |
I suspect this needs an actual RFC. However, with the newly-fixed method dispatch, I don't expect any obstacles to implementing this. |
I mean, for implementing it in method dispatch. The interesting part that actually needs the RFC is the compiler being able to downcast the With the current ABI, this is basically done in the compiler-generated impl of Maybe have the compiler do a reverse unsized coercion? That's it, we can have this object safety rule:
Actually, I'm not sure that would work, because you might have the unsized coercion go through a different Unsize impl, say using an associated type (e.g. the example from #44861). We ICE on that (in trans), so maybe there's good room to lock things up somewhat. Or maybe just add an additional trait: pub trait CoerceSized<Target> {
type SizeSource: ?Sized;
type SizeTarget: Unsize<Self::SizeSource>;
} and have the bound be
I believe we can then implement
Or maybe there's another solution I'm missing. |
Lang team meeting: an RFC is needed prior to stabilization, but we're happy to accept experimentatal implementation in the meantime. |
Implement arbitrary_self_types r? @arielb1 cc @nikomatsakis Partial implementation of #44874. Supports trait and struct methods with arbitrary self types, as long as the type derefs (transitively) to `Self`. Doesn't support raw-pointer `self` yet. Methods with non-standard self types (i.e. anything other than `&self, &mut self, and Box<Self>`) are not object safe, because dynamic dispatch hasn't been implemented for them yet. I believe this is also a (partial) fix for #27941.
@arielb1 Is there any progress on an object-safe implementation of this?
I'm not sure I fully understand the syntax here but it seems like you also want to pass trait MyTrait {
fn foo(self: &Rc<Self>, arg: String);
}
struct Thing;
impl MyTrait for Thing {
fn foo(self: &Rc<Self>, arg: String) {
unimplemented!()
}
} Would create a vtable with So a "correct" impl signature would look something like this, but it is kinda ugly. impl MyTrait for Thing {
fn foo(self: &Rc<MyTrait>, inner_self: &Self, arg: String) {
unimplemented!()
}
} Also I have been really sloppy about throwing |
Not really. Someone needs to work on that. |
The diagnostic seems improved so I'm closing in favor of #44874. |
The book states:
The reference uses typed self in a few places, but doesn't explain the exact rules.
The compiler also prints redundant and misleading diagnostics:
gives:
Since replacing
Vec<Self>
withBox<Self>
makes the code compile, "expected structS
" isn't quite correct.The text was updated successfully, but these errors were encountered: