Reputation: 6449
I have two Vectors of Tuples:
let nice_nums: Vec<(u16, u32)> = vec![(1, 10), (2, 11)];
let better_nums: Vec<(u16, u32)> = vec![(3, 12), (4, 13), (1, 8)];
I would like to merge better_nums
with nice_nums
but better_nums
should take precedence. If the first value (u16) in any of the better_nums
tuples matches any first value in the nice_nums
tuple then the tuple that belongs to better_nums
should take precedence and be added instead of the nice_nums
tuple with the same key.
I tried to do this but I am not super familiar with Rust syntax:
// merged_numbers should be [(2, 11), (3, 12), (4, 13), (1, 8)]
let merged_numbers = better_nums.iter().map(|(a, b)| {
for (i, j) in nice_nums {
if i == a {
return (a, b)
}
return (i, j)
}
}).cloned().collect();
Upvotes: 1
Views: 746
Reputation: 70990
You can do that with iterators:
let nice_nums: Vec<(u16, u32)> = vec![(1, 10), (2, 11)];
let better_nums: Vec<(u16, u32)> = vec![(3, 12), (4, 13), (1, 8)];
let mut result = better_nums.clone();
result.extend(nice_nums.iter().copied().filter(|nice_tuple| {
!better_nums
.iter()
.any(|better_tuple| better_tuple.0 == nice_tuple.0)
}));
Upvotes: 1
Reputation: 42708
If order doesn't matter, you can use a HashMap
as intermediary, inserting better_nums
after to keep those values:
use std::collections::HashMap;
fn main() {
let nice_nums: Vec<(u16, u32)> = vec![(1, 10), (2, 11)];
let better_nums: Vec<(u16, u32)> = vec![(3, 12), (4, 13), (1, 8)];
let result: Vec<(u16, u32)> = nice_nums
.into_iter()
.chain(better_nums.into_iter())
.collect::<HashMap<u16, u32>>()
.into_iter()
.collect();
println!("{result:?}");
}
[(2, 11), (4, 13), (3, 12), (1, 8)]
Upvotes: 2
Reputation: 2854
I don't know if this is the most idiomatic way in Rust, but this works:
fn main() {
let nice_nums: Vec<(u16, u32)> = vec![(1, 10), (2, 11)];
let better_nums: Vec<(u16, u32)> = vec![(3, 12), (4, 13), (1, 8)];
// at the minimum, merged will include all of your `better_nums`
let mut merged = better_nums.clone();
nice_nums.iter().for_each(|&tup1| {
// if the first element of our `nice_num` matches one of the `better_nums`
// then do nothing. if there are no matches, add our `nice_num` to
// `merged`
for &tup2 in better_nums.iter() {
if tup1.0 == tup2.0 {
return;
}
}
merged.push(tup1);
});
println!("{:?}", merged); // [(3, 12), (4, 13), (1, 8), (2, 11)]
}
Upvotes: 1