Skip to content
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

Compiler requires redundant trait bounds which should be inferrable #58214

Closed
joshlf opened this issue Feb 6, 2019 · 4 comments
Closed

Compiler requires redundant trait bounds which should be inferrable #58214

joshlf opened this issue Feb 6, 2019 · 4 comments

Comments

@joshlf
Copy link
Contributor

joshlf commented Feb 6, 2019

The following program should compile, but doesn't:

pub trait Foo: Iterator
where
    <Self as Iterator>::Item: Clone,
{
}

#[derive(Clone)]
struct MyWrapper<T>(T);

impl<T: Foo> Foo for MyWrapper<T> {}

impl<T: Foo> Iterator for MyWrapper<T> {
    type Item = T::Item;

    fn next(&mut self) -> Option<T::Item> {
        self.0.next()
    }
}

In particular, rustc seems unable to infer that the T: Foo bound in each of the two impl blocks implies that <T as Iterator>::Item: Clone:

error[E0277]: the trait bound `<T as std::iter::Iterator>::Item: std::clone::Clone` is not satisfied
  --> src/lib.rs:10:14
   |
10 | impl<T: Foo> Foo for MyWrapper<T> {}
   |              ^^^ the trait `std::clone::Clone` is not implemented for `<T as std::iter::Iterator>::Item`
   |
   = help: consider adding a `where <T as std::iter::Iterator>::Item: std::clone::Clone` bound

error[E0277]: the trait bound `<T as std::iter::Iterator>::Item: std::clone::Clone` is not satisfied
  --> src/lib.rs:12:1
   |
12 | / impl<T: Foo> Iterator for MyWrapper<T> {
13 | |     type Item = T::Item;
14 | |
15 | |     fn next(&mut self) -> Option<T::Item> {
16 | |         self.0.next()
17 | |     }
18 | | }
   | |_^ the trait `std::clone::Clone` is not implemented for `<T as std::iter::Iterator>::Item`
   |
   = help: consider adding a `where <T as std::iter::Iterator>::Item: std::clone::Clone` bound
note: required by `Foo`
  --> src/lib.rs:1:1
   |
1  | / pub trait Foo: Iterator
2  | | where
3  | |     <Self as Iterator>::Item: Clone,
4  | | {
5  | | }
   | |_^

error[E0277]: the trait bound `<T as std::iter::Iterator>::Item: std::clone::Clone` is not satisfied
  --> src/lib.rs:15:5
   |
15 | /     fn next(&mut self) -> Option<T::Item> {
16 | |         self.0.next()
17 | |     }
   | |_____^ the trait `std::clone::Clone` is not implemented for `<T as std::iter::Iterator>::Item`
   |
   = help: consider adding a `where <T as std::iter::Iterator>::Item: std::clone::Clone` bound
note: required by `Foo`
  --> src/lib.rs:1:1
   |
1  | / pub trait Foo: Iterator
2  | | where
3  | |     <Self as Iterator>::Item: Clone,
4  | | {
5  | | }
   | |_^

If, however, we take rustc's advice and add where <T as Iterator>::Item: Clone bounds, it compiles.

This seems like a bug to me, since the bound we added should be implied by the T: Foo bound.

@jonas-schievink
Copy link
Contributor

This is a known issue, rustc was never able to propagate bounds like this. Blocked on chalk AFAIK, and also might need an RFC.

@joshlf
Copy link
Contributor Author

joshlf commented Feb 6, 2019

Gotcha. Is this tracked in an issue somewhere so I can close as a duplicate of that?

@jonas-schievink
Copy link
Contributor

I know we've closed a few dupes of this, but I don't know if there's a canonical issue for this

@varkor
Copy link
Member

varkor commented Feb 6, 2019

This is implied bounds.

@varkor varkor closed this as completed Feb 6, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants