I'm trying to create an iterator that will add one element to the start of a vector
struct World {
player: Object,
npcs: Vec<Object>,
}
impl World {
pub fn all_objects(&mut self) -> ???
}
I understand I need to use the chain
function for this but I'm not sure how, or what will the return type be
Maybe someone can explain to me how to use it?
The exact types of iterators can be complex. A fast way to determine them is to try to return the wrong type on purpose, and see what the compiler says:
struct Object;
struct World {
player: Object,
npcs: Vec<Object>,
}
impl World {
pub fn all_objects(&mut self) -> () {
std::iter::once(&self.player).chain(self.npcs.iter())
}
}
This gives:
error[E0308]: mismatched types
--> src/lib.rs:10:9
|
9 | pub fn all_objects(&mut self) -> () {
| -- expected `()` because of return type
10 | std::iter::once(&self.player).chain(self.npcs.iter())
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^- help: try adding a semicolon: `;`
| |
| expected `()`, found struct `std::iter::Chain`
|
= note: expected unit type `()`
found struct `std::iter::Chain<std::iter::Once<&Object>, std::slice::Iter<'_, Object>>`
and indeed if you replace that, it will compile:
struct Object;
struct World {
player: Object,
npcs: Vec<Object>,
}
impl World {
pub fn all_objects(
&mut self,
) -> std::iter::Chain<std::iter::Once<&Object>, std::slice::Iter<'_, Object>> {
std::iter::once(&self.player).chain(self.npcs.iter())
}
}
But the exact type usually doesn't matter with iterators, so you can simply specify that your function returns some kind of iterator:
struct Object;
struct World {
player: Object,
npcs: Vec<Object>,
}
impl World {
pub fn all_objects(&mut self) -> impl Iterator<Item = &Object> {
std::iter::once(&self.player).chain(self.npcs.iter())
}
}
This is also more flexible, as it will let you change the implementation without affecting the users of the function.
Collected from the Internet
Please contact [email protected] to delete if infringement.
Comments