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

Type inference fails to infer the type of a closure when calling a function with an argument bounded by a trait implemented for a closure which takes a reference argument #24735

Closed
bstrie opened this issue Apr 23, 2015 · 1 comment
Labels
A-closures Area: Closures (`|…| { … }`)

Comments

@bstrie
Copy link
Contributor

bstrie commented Apr 23, 2015

This code fails to compile:

trait Foo {}

impl<T: Fn(&())> Foo for T {}

fn baz<T: Foo>(_: T) {}

fn main() {
    baz(|_| ());
}

Error message:

hrt.rs:8:5: 8:8 error: type mismatch resolving `for<'r> <[closure hrt.rs:8:9: 8:15] as core::ops::FnOnce<(&'r (),)>>::Output == ()`:
 expected bound lifetime parameter ,
    found concrete lifetime [E0271]
hrt.rs:8     baz(|_| ());
             ^~~
hrt.rs:8:5: 8:8 note: required by `baz`
hrt.rs:8     baz(|_| ());
             ^~~
hrt.rs:8:5: 8:8 error: type mismatch: the type `[closure hrt.rs:8:9: 8:15]` implements the trait `core::ops::Fn<(_,)>`, but the trait `for<'r> core::ops::Fn<(&'r (),)>` is required (expected concrete lifetime, found bound lifetime parameter ) [E0281]
hrt.rs:8     baz(|_| ());
             ^~~
hrt.rs:8:5: 8:8 note: required by `baz`
hrt.rs:8     baz(|_| ());
             ^~~
error: aborting due to 2 previous errors

This error can be solved by explicitly annotating the type of the closure:

trait Foo {}

impl<T: Fn(&())> Foo for T {}

fn baz<T: Foo>(_: T) {}

fn main() {
    baz(|_: &()| ());  // with explicit type annotation, this code compiles
}

This problem does not arise when the argument to the closure is not behind a reference:

trait Foo {}

impl<T: Fn(())> Foo for T {}  // lacking a reference argument, this code compiles

fn baz<T: Foo>(_: T) {}

fn main() {
    baz(|_| ());
}

This error first observed in @brson's blog "httptest" blog post: https://github.com/brson/httptest#4-mutation , where it is described as a bug in type inference rather than an inherent limitation of the type system.

@bstrie bstrie added the A-closures Area: Closures (`|…| { … }`) label Apr 23, 2015
@bstrie
Copy link
Contributor Author

bstrie commented Apr 23, 2015

Closing as a dupe of #24680.

@bstrie bstrie closed this as completed Apr 23, 2015
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-closures Area: Closures (`|…| { … }`)
Projects
None yet
Development

No branches or pull requests

1 participant