I have the following code, which fails to compile due to lifetime error.
use std::marker::PhantomData;
trait Exampler<'a> {
fn new(d: &'a u8) -> Self;
fn get_best<'f>(&self, vals: impl Iterator<Item = &'f u8>) -> &'f u8;
}
struct Foo<'a>(&'a u8);
impl<'a> Exampler<'a> for Foo<'a> {
fn new(d: &'a u8) -> Self {
Foo(d)
}
fn get_best<'f>(&self, mut vals: impl Iterator<Item = &'f u8>) -> &'f u8 {
vals.next().unwrap()
}
}
struct Bar<E>(PhantomData<E>);
impl<'a, E> Bar<E>
where E: Exampler<'a> {
pub fn foobar(self) -> u8 {
let i = 0u8;
static u8s: &[u8] = &[1,2,3,4,5];
let e = E::new(&i);
*e.get_best(u8s.into_iter())
}
}
pub fn main() {
Bar::<Foo>(PhantomData).foobar();
}
error[E0597]: `i` does not live long enough
--> src/main.rs:26:24
|
21 | impl<'a, E> Bar<E>
| -- lifetime `'a` defined here
...
26 | let e = E::new(&i);
| -------^^-
| | |
| | borrowed value does not live long enough
| argument requires that `i` is borrowed for `'a`
27 | *e.get_best(u8s.into_iter())
28 | }
| - `i` dropped here while still borrowed
In order to address this problem, I tried HRTB with
impl<E> Bar<E>
where E: for<'a> Exampler<'a>
which also fails to compile because of
error[E0599]: no method named `foobar` found for struct `Bar<Foo<'_>>` in the current scope
--> src/main.rs:32:29
|
8 | struct Foo<'a>(&'a u8);
| ----------------------- doesn't satisfy `Foo<'_>: Exampler<'a>`
...
19 | struct Bar<E>(PhantomData<E>);
| ------------------------------ method `foobar` not found for this
...
32 | Bar::<Foo>(PhantomData).foobar();
| ^^^^^^ method not found in `Bar<Foo<'_>>`
|
= note: the method `foobar` exists but the following trait bounds were not satisfied:
`Foo<'_>: Exampler<'a>`
I think this is because actually Foo<'a>
effectively uses the lifetime 'a
in Exampler<'a>
, so the for<'a>
is not valid for Foo<'a>: Exampler<'a>
.
I wonder how to get this compiled, thanks for your possible help.