Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
1.1k views
in Technique[技术] by (71.8m points)

rust - Why does a for loop not require a mutable iterator?

If I want to consume an iterator by hand, it has to be mutable:

let test = vec![1, 2, 3];
let mut test_mut = test.iter();
while let Some(val) = test_mut.next() {
    println!("{:?}", val);
}

But I can happily consume it with a for loop, even if it's immutable.

let test = vec![1, 2, 3];
let test_imm = test.iter();
for val in test_imm {
    println!("{:?}", val);
}

I think this works because test_imm is moved into the for loop's block, so test_imm can't be used by the outer block any more and is (from the point of view of the outer block) immutable up until the for loop, and then it's inaccessible, so it's okay.

Is that right? Is there more to be explained?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

That's exactly right. Since it's moved to the for loop, the for loop now owns it and can do whatever it wants with it, including "making it" mutable. Consider this analogous example, where we appear to be mutating xs despite it being immutable, but really it's because we're moving it, so the new owner is free to do with it whatever it wants, including re-binding it as mutable:

let xs: Vec<i32> = vec![1, 2, 3];

fn append(v: Vec<i32>, x: i32) -> Vec<i32> {
    let mut my_v = v;
    my_v.push(x);
    my_v
}

let appended = append(xs, 4);

playground

Note that the function can be made shorter using the mut parameter convenience syntax:

fn append(mut v: Vec<i32>, x: i32) -> Vec<i32> {
    v.push(x);
    v
}

This is more or less explained in the iter module's documentation.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...