Implement chain() for a Lending Iterator (GAT)

I am trying to implement an Iterator::chain()-like operation for a lending iterator (Using #![feature(generic_associated_types)]):

#![feature(generic_associated_types)]

pub trait LendingIterator {
	type Item<'a> where Self: 'a;

	fn next(&mut self) -> Option<Self::Item<'_>>;
}

To do this, similarly to the normal Iterator::chain(), I need a struct Chain that contains the two chained LendingIterators and impl's LendingIterator.

The problem I have is I need to specify the iterator types A and B having matching Item generic associated types, so I tried this:

pub struct Chain<A, B> {
	a: Option<A>,
	b: Option<B>,
}

impl<A, B> LendingIterator for Chain<A, B>
    where
        A: LendingIterator,
        B: for<'a> LendingIterator<Item<'a>=A::Item<'a>>
{
	type Item<'a> where Self: 'a = A::Item<'a>;

	fn next(&mut self) -> Option<Self::Item<'_>> {
        todo!()
	}
}

But I get:

error[E0311]: the parameter type `B` may not live long enough
  --> src\lib.rs:63:12
   |
63 | impl<A, B> LendingIterator for Chain<A, B> where A: LendingIterator, B: for<'a> LendingIterator<Item<'a>=A::Item<'a>> {
   |         -  ^^^^^^^^^^^^^^^ ...so that the type `B` will meet its required lifetime bounds...
   |         |
   |         help: consider adding an explicit lifetime bound...: `B: 'a`
   |
note: ...that is required by this bound
   |        ^^^^ ...so that the type `B` will meet its required lifetime bounds

Of course the compiler's suggestions don't seem to work.

How can I add the constraint that B does have a long enough lifetime?

4 Likes

Turns out this is a bug in rust's GAT implementation. See this:

"rust-lang"

"rust-lang"