简体   繁体   中英

How to hold a Peekable of any iterator in a struct?

I have a struct:

struct Quads<'a> {
    mx: &'a Vec<Vec<u32>>,
    xs: &'a mut Peekable<Range<i32>>,
    ys: &'a mut Peekable<Range<i32>>,
    dx: i32,
    dy: i32,
}

I wanted the type of xs to be Peekable<dyn Iterator<Item = i32>> , as that would be a natural thing to want in other languages. Is such an idea expressible in Rust?

That is, "a Peekable of some Iterator of i32 ", not a Peekable of a specific Iterator .

The problem with Peekable<dyn Iterator<Item = i32>> is that dyn Trait represents a type dynamically (obviously) which means that it is a dynamically sized type . Those cannot be expressed directly as a struct field (except through obscure means).

So @edwardw's comment is the way to go. Putting the iterator in a Box ensures the field has a fixed size but the iterator itself can be whatever size it wants. Box also naturally implements Iterator if the contents implement Iterator . Here's the changes (also following your lead in your other Q&A that they should be stored directly and not as &mut references):

struct Quads<'a> {
    mx: &'a Vec<Vec<u32>>,
    xs: Peekable<Box<dyn Iterator<Item = i32>>>,
    ys: Peekable<Box<dyn Iterator<Item = i32>>>,
    dx: i32,
    dy: i32,
}

Which you can then create via Box::new(0..dx) as Box<dyn Iterator<Item = i32>> ( playground ).

If the expected concrete type is Range<i32> then this probably isn't a problem, but if you did want to store more exotic iterators that require lifetimes, then you may need to add a + 'a constraint as shown in this answer: How can I make Box<dyn Iterator> peekable and avoid lifetime errors?

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM