<html><head><meta http-equiv="Content-Type" content="text/html charset=windows-1252"></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;"><div>`mut_iter` only gives you mutable references to the elements of the container; it doesn’t allow you to reborrow the container itself mutably inside of the loop.</div><div><br></div><div>Cameron</div><div><br></div><div><div>On Jun 1, 2014, at 1:39 PM, Christophe Pedretti <<a href="mailto:christophe.pedretti@gmail.com">christophe.pedretti@gmail.com</a>> wrote:</div><br class="Apple-interchange-newline"><blockquote type="cite"><div dir="ltr">and using mut_iter() instead of iter() is not enough ?<div class="gmail_extra"><br><br><div class="gmail_quote">2014-06-01 22:03 GMT+02:00 Cameron Zwarich <span dir="ltr"><<a href="mailto:zwarich@mozilla.com" target="_blank">zwarich@mozilla.com</a>></span>:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">The simplest thing to do is probably to build an intermediate vector of vertices to insert and then push them all after you are done iterating over the edges.<br>

<span class="HOEnZb"><font color="#888888"><br>
Cameron<br>
</font></span><div class="HOEnZb"><div class="h5"><br>
> On Jun 1, 2014, at 12:48 PM, Nicholas Bishop <<a href="mailto:nicholasbishop@gmail.com">nicholasbishop@gmail.com</a>> wrote:<br>
><br>
> I'm looking for a little borrow-checker advice. Here's a reasonably<br>
> minimal program that demonstrates the problem:<br>
><br>
> extern crate collections;<br>
><br>
> use collections::HashMap;<br>
><br>
> struct G {<br>
>   verts: HashMap<int, String>,<br>
>   edges: Vec<(int, int)>,<br>
><br>
>   next_vert_id: int<br>
> }<br>
><br>
> impl G {<br>
>   fn new() -> G {<br>
>       G{verts: HashMap::new(), edges: Vec::new(), next_vert_id: 0}<br>
>   }<br>
><br>
>   fn add_vert(&mut self, s: &str) -> int {<br>
>       let id = self.next_vert_id;<br>
>       self.next_vert_id += 1;<br>
>       self.verts.insert(id, String::from_str(s));<br>
>       id<br>
>   }<br>
><br>
>   fn add_edge(&mut self, v0: int, v1: int) {<br>
>       self.edges.push((v0, v1))<br>
>   }<br>
> }<br>
><br>
> fn main() {<br>
>   let mut g = G::new();<br>
><br>
>   {<br>
>       let v0 = g.add_vert("vert 0");<br>
>       let v1 = g.add_vert("vert 1");<br>
>       g.add_edge(v0, v1);<br>
>   }<br>
><br>
>   for &(v0, v1) in g.edges.iter() {<br>
>       g.add_vert("edge vert");<br>
>   }<br>
> }<br>
><br>
> This fails to compile:<br>
> $ rust-nightly-x86_64-unknown-linux-gnu/bin/rustc -v<br>
> rustc 0.11.0-pre-nightly (064dbb9 2014-06-01 00:56:42 -0700)<br>
> host: x86_64-unknown-linux-gnu<br>
><br>
> $ rust-nightly-x86_64-unknown-linux-gnu/bin/rustc <a href="http://graph.rs/" target="_blank">graph.rs</a><br>
> graph.rs:39:9: 39:10 error: cannot borrow `g` as mutable because<br>
> `g.edges` is also borrowed as immutable<br>
> <a href="http://graph.rs:39/" target="_blank">graph.rs:39</a>         g.add_vert("edge vert");<br>
>                   ^<br>
> graph.rs:38:22: 38:29 note: previous borrow of `g.edges` occurs here;<br>
> the immutable borrow prevents subsequent moves or mutable borrows of<br>
> `g.edges` until the borrow ends<br>
> <a href="http://graph.rs:38/" target="_blank">graph.rs:38</a>     for &(v0, v1) in g.edges.iter() {<br>
>                                ^~~~~~~<br>
> graph.rs:41:2: 41:2 note: previous borrow ends here<br>
> <a href="http://graph.rs:38/" target="_blank">graph.rs:38</a>     for &(v0, v1) in g.edges.iter() {<br>
> <a href="http://graph.rs:39/" target="_blank">graph.rs:39</a>         g.add_vert("edge vert");<br>
> <a href="http://graph.rs:40/" target="_blank">graph.rs:40</a>     }<br>
> <a href="http://graph.rs:41/" target="_blank">graph.rs:41</a> }<br>
>           ^<br>
> error: aborting due to previous error<br>
><br>
> My understanding of the error is: G::add_vert is being given a mutable<br>
> reference to "g", which means it could do something naughty like clear<br>
> g.edges, which would screw up the loop iteration that is happening in<br>
> main().<br>
><br>
> That seems like a pretty reasonable thing to prevent, but it's not<br>
> clear to me how I should restructure the program to work around the<br>
> error. In this minimal example I could copy the code out of<br>
> G::add_vert and stick it directly inside the loop, but that's clearly<br>
> not the general solution.<br>
><br>
> Thanks,<br>
> -Nicholas<br>
> _______________________________________________<br>
> Rust-dev mailing list<br>
> <a href="mailto:Rust-dev@mozilla.org">Rust-dev@mozilla.org</a><br>
> <a href="https://mail.mozilla.org/listinfo/rust-dev" target="_blank">https://mail.mozilla.org/listinfo/rust-dev</a><br>
_______________________________________________<br>
Rust-dev mailing list<br>
<a href="mailto:Rust-dev@mozilla.org">Rust-dev@mozilla.org</a><br>
<a href="https://mail.mozilla.org/listinfo/rust-dev" target="_blank">https://mail.mozilla.org/listinfo/rust-dev</a><br>
</div></div></blockquote></div><br></div></div>
_______________________________________________<br>Rust-dev mailing list<br><a href="mailto:Rust-dev@mozilla.org">Rust-dev@mozilla.org</a><br>https://mail.mozilla.org/listinfo/rust-dev<br></blockquote></div><br></body></html>