I would like to have a function that takes a callback, and the callback takes and returns a reference. The problem is, the reference is going to be created inside my function, so I can't declare the lifetime on the function itself.
For a callback that returns a concrete type I can use for<'a> F: FnOnce(&'a X) -> Something<'a>
, but the for<'a>
syntax doesn't seem to work with generic types. I've tried for<'a> F: FnOnce(&'a X) -> U + 'a
and for<'a> F: FnOnce(&'a X) -> U, U: 'a
, but neither of them has the meaning I want.
Here's a minimal test case (playground link).
struct ReferenceHolder<'a> {
pub x: &'a u32,
}
trait NumberMaker {
fn make(self) -> u32;
}
impl<'a> NumberMaker for ReferenceHolder<'a> {
fn make(self) -> u32 {
*self.x
}
}
fn something_owning_value_by_reference<X, F>(x: X, f: F) -> u32
where
for<'a> F: FnOnce(&'a X) -> ReferenceHolder<'a>,
{
f(&x).make()
}
fn something_owning_value_by_reference_generic<X, F, R>(x: X, f: F) -> u32
where
for<'a> F: FnOnce(&'a X) -> R,
R: NumberMaker
{
f(&x).make()
}
fn main() {
let test = 42u32;
// this works with concrete type
println!("{}", something_owning_value_by_reference(test, |x| ReferenceHolder{x: x}));
// this fails with generic type
println!("{}", something_owning_value_by_reference_generic(test, |x| ReferenceHolder{x: x}));
}
The actual problem is about async fn
callback using the reference, and the generic type is impl Future
that needs to reflect that.