I'm trying to make the following compile (without getting rid of the Bar
trait alias):
trait_set::trait_set! {
pub trait Bar = Fn(&[u32]);
}
/* Expands to
pub trait Bar: Fn(&[u32]) {}
impl<T: Fn(&[u32])> Bar for T {}
*/
fn foo(bar: impl Bar) {
bar(&vec![1]);
}
fn main() {
foo(|a| println!("{:?}", a));
}
Compiling the above code as-is yields the following error:
error[E0308]: mismatched types
--> src/main.rs:10:5
|
10 | foo(|a| println!("{:?}", a));
| ^^^ lifetime mismatch
|
= note: expected type `for<'r> Fn<(&'r [u32],)>`
found type `Fn<(&[u32],)>`
// [...]
If I understand the error message correctly, then the problem is that the Bar
trait requires the implementing function to take a reference with any arbitrary lifetime, while the closure that I pass to foo()
only accepts a reference with lifetime equal to the duration of the function call. So I believe my question is, how can I tell Rust that the latter lifetime requirement is good enough for my Bar
trait?
Btw, it's worth noting that this compiles:
fn foo(bar: impl Fn(&[u32])) {
bar(&vec![1]);
}
fn main() {
foo(|a| println!("{:?}", a));
}
So the problem only arises if I move the Fn(...)
bound into a trait alias.