Search code examples
rustiterator

How to zip two iterators of unequal length with a default?


I'm trying to zip two iterators of unequal length, it only returns when when there is value in both and ignores the rest in the longest iterator.

fn main() {
    let num1 = vec![1, 2];
    let num2 = vec![3];

    for i in num1.iter().rev().zip(num2.iter().rev()) {
        println!("{:?}", i);
    }
}

This returns (2, 3). How do i make it return:

(2, 3)
(1, 0) // default is the 0 here.

Is there any other way to do it?


Solution

  • You could use the zip_longest provided by the itertools crate.

    use itertools::{
        Itertools,
        EitherOrBoth::*,
    };
    
    fn main() {
        let num1 = vec![1, 2];
        let num2 = vec![3];
    
        for pair in num1.iter().rev().zip_longest(num2.iter().rev()) {
            match pair {
                Both(l, r) => println!("({:?}, {:?})", l, r),
                Left(l) => println!("({:?}, 0)", l),
                Right(r) => println!("(0, {:?})", r),
            }
        }
    }
    

    Which would produce the following output:

    (2, 3)
    (1, 0)