I want to define a trait that's a subtrait of std::ops::Index
for a concrete reference type, e.g. something like this:
trait RefIndex<'a>: Index<&'a usize> {}
Which I can do, however, when I try to use it like:
fn get_sum<'a>(inp: impl RefIndex<'a, Output = u64>) -> u64 {
let mut sum = 0;
for i in 0..1 {
sum += inp[&i];
}
sum
}
I get
5 | fn get_sum<'a>(inp: impl RefIndex<'a, Output = u64>) -> u64 {
| -- lifetime `'a` defined here
...
8 | sum += inp[&i];
| ^^
| |
| borrowed value does not live long enough
| requires that `i` is borrowed for `'a`
9 | }
| - `i` dropped here while still borrowed
I think this indicates that rust thinks the implementation of Index
is only valid for references that live as long as get_sum
when really I only want it for the transient lifetime of the function call. However, I'm not sure how to annotate RefIndex
(or get_sum
) in such a way to define that as the appropriate lifetime.
Note, for concrete types this problem doesn't happen, rust is able to infer the reduced lifetime of the reference and the following compiles just fine:
struct MyVec<T>(Vec<T>);
impl<T> Index<&usize> for MyVec<T> {
type Output = T;
fn index(&self, ind: &usize) -> &T {
&self.0[*ind]
}
}
fn get_sum_vec(inp: MyVec<u64>) -> u64 {
let mut sum = 0;
for i in 0..1 {
sum += inp[&i];
}
sum
}