Info
This post is auto-generated from RSS feed The Rust Programming Language Forum - Latest topics. Source: Implied lifetime bound of associated types
I just hit problem with satisfying the lifetime bound of a generic type parameter that's fed into the GAT of the trait it is implementing. When I write impl <T, CST> CoordsIter for CST where CST: CoordSeqTrait<T = T>
, there seems to be no lifetime bound applied to T
, but when I instead use CST::T
inside the impl, T
seems to have a lifetime bound. Here is an example with code that does not compile and a variant that compiles (Playground):
#[derive(Copy, Clone)]
struct Coord<T> {
x: T,
y: T,
}
trait CoordsIter {
type Iter<'a>: Iterator<Item = Coord<Self::Scalar>>
where
Self: 'a;
type Scalar;
fn coords_iter(&self) -> Self::Iter<'_>;
}
// Same as CoordsIter, but with a different name.
trait CoordsIter2 {
type Iter<'a>: Iterator<Item = Coord<Self::Scalar>>
where
Self: 'a;
type Scalar;
fn coords_iter(&self) -> Self::Iter<'_>;
}
trait CoordSeqTrait {
type T;
}
// This does not compile.
impl<T, CST> CoordsIter for CST
where
CST: CoordSeqTrait<T = T>,
{
type Iter<'a> = Box<dyn Iterator<Item = Coord<T>> + 'a>
where
Self: 'a;
type Scalar = T;
// error[E0311]: the parameter type `T` may not live long enough
// --> src/coords_iter.rs:65:9
// |
// 61 | fn coords_iter(&self) -> Self::Iter<'_> {
// | ----- the parameter type `T` must be valid for the anonymous lifetime defined here...
// ...
// 65 | Box::new(iter)
// | ^^^^^^^^^^^^^^ ...so that the type `T` will meet its required lifetime bounds
// |
// help: consider adding an explicit lifetime bound
// |
// 61 - fn coords_iter(&self) -> Self::Iter<'_> {
// 61 + fn coords_iter<'a>(&'a self) -> Self::Iter<'a> where T: 'a {
// |
fn coords_iter(&self) -> Self::Iter<'_> {
let all_coords: Vec<Coord<T>> = vec![];
let iter = all_coords.into_iter();
Box::new(iter)
}
}
// This compiles.
impl<CST> CoordsIter2 for CST
where
CST: CoordSeqTrait,
{
type Iter<'a>
= Box<dyn Iterator<Item = Coord<CST::T>> + 'a>
where
Self: 'a;
type Scalar = CST::T;
fn coords_iter(&self) -> Self::Iter<'_> {
let all_coords: Vec<Coord<CST::T>> = vec![];
let iter = all_coords.into_iter();
Box::new(iter)
}
}
It seems to me that type T
in CST::T
has some implicit lifetime bound so it is not fully equivalent to defining a generic type parameter T
and bound it using CST: CoordSeqTrait<T = T>
, but I cannot find any reference to this implicit rule. I'd like to get explanations why these 2 impls are not equivalent, and relevant rules for lifetimes of associated types.
1 post - 1 participant
🏷️ rust_feed