I'm trying to build a vector of points that are changed while iterating over them:
struct Point {
x: i16,
y: i16,
}
fn main() {
let mut points: Vec<Point> = vec![];
// unsure if point is mutable
points.push(Point { x: 10, y: 10 });
// thus trying it explicitly
let mut p1 = Point { x: 20, y: 20 };
points.push(p1);
for i in points.iter() {
println!("{}", i.x);
i.x = i.x + 10;
}
}
When compiling, I get the error:
error[E0594]: cannot assign to immutable field `i.x`
--> src/main.rs:16:9
|
16 | i.x = i.x + 10;
| ^^^^^^^^^^^^^^ cannot mutably borrow immutable field
As I learned here, Rust doesn't allow modifying the structure while iterating over it, thus the error.
How do I modify it in an elegant way? If I read this answer and get it right then the following comes to my mind:
- pop the item from the vector, modify it and push it back.
- create a temporary structure where I push the changed items to and replace original structure with the temporary one outside the loop (how?).
While I think I can get (1) working, I'm not really happy about all this pop's and push's (is this high-performance anyhow?). Concerning (2), I have no idea how to get it working - if this would work at all.
Questions:
- Is (2) an solution and if yes, how would it look like?
- Are there any other solutions?
- What's the advantage or disadvantage of the different solutions, especially with respect to performance?
for i in &mut points
since it uses theIntoIterator
trait. – Outlier