Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Closures and Higher-Ranked-Trait-Bounds lifetime issue

Tags:

rust

I am experimenting with higher-ranked-trait bounds. In a minimal example, I created, there is a function taking a closure which takes a &str and returning a &str of the same lifetime 'a. I explicitly declared the lifetimes on the Fn trait.

fn foo(_: &for<'a> Fn(&'a str) -> &'a str) {
}

fn main() {
    foo(&|s| s);
}

This works fine. If I annotate the type of the parameter in the closure to be of type &str, I receive a lifetime error:

fn foo(_: &for<'a> Fn(&'a str) -> &'a str) {
}

fn main() {
    foo(&|s: &str| s); // explicitly specified parameter type
}

That confuses me. For several reasons.

  • Isn't the return type of the closure inferred to be of the same type as the parameter (with the same lifetime via lifetime elision)?
  • The argument of foo is univerally quantified over all possible lifetimes. Why can't the type of the lifetime be arbitrary? Isn't 'a just a placeholder for some lifetime?

It works without specifying the type explicitly, but why? How are those two versions different?

playpen code

like image 252
jtepe Avatar asked Oct 27 '15 09:10

jtepe


1 Answers

At current version of Rust this compiles without warnings:

fn foo<T>(_: &T) where
T: for<'a> Fn(&'a str) -> &'a str
{
}

fn main() {
    foo(&|s: &str| s); // explicitly specified parameter type
}
like image 187
Angelicos Phosphoros Avatar answered Oct 31 '22 04:10

Angelicos Phosphoros