Caleb Stanford already covered how you could improve the type of loop you wrote, but since you asked about other Rust features and how you might use them here, I’ll cover those.
Rust’s type system makes us get really pedantic, but it can deduce a lot of things itself, and there is a reason for all of it. In this example, we need to create Peekable input iterators, to be able to test and compare their values without advancing the iterators. Output iterators always need to borrow the data they reference mutably. The iterators themselves must also be mut, so we can advance them. Calling next or peek on them returns an Option, and since the iterator is to a borrowed container of i32, it’s an Option<&i32> and we need to dereference the value inside Some. Finally, I chose (unlike LeetCode) to return the output slice, which is very useful to chain and compose merge operations. But, any reference we return in Rust needs a lifetime. In this case, we’re returning the output slice that we received, so we give its lifetime a name and use that. Most people give lifetimes names like <'a, 'b>, but if I wouldn’t name a variable that way, I don’t name a lifetime that way either.