1 You tried to move out of a value which was borrowed.
3 This can also happen when using a type implementing `Fn` or `FnMut`, as neither
4 allows moving out of them (they usually represent closures which can be called
5 more than once). Much of the text following applies equally well to non-`FnOnce`
8 Erroneous code example:
11 use std::cell::RefCell;
16 fn nothing_is_true(self) {}
20 let x = RefCell::new(TheDarkKnight);
22 x.borrow().nothing_is_true(); // error: cannot move out of borrowed content
26 Here, the `nothing_is_true` method takes the ownership of `self`. However,
27 `self` cannot be moved because `.borrow()` only provides an `&TheDarkKnight`,
28 which is a borrow of the content owned by the `RefCell`. To fix this error,
29 you have three choices:
31 * Try to avoid moving the variable.
32 * Somehow reclaim the ownership.
33 * Implement the `Copy` trait on the type.
38 use std::cell::RefCell;
43 fn nothing_is_true(&self) {} // First case, we don't take ownership
47 let x = RefCell::new(TheDarkKnight);
49 x.borrow().nothing_is_true(); // ok!
56 use std::cell::RefCell;
61 fn nothing_is_true(self) {}
65 let x = RefCell::new(TheDarkKnight);
66 let x = x.into_inner(); // we get back ownership
68 x.nothing_is_true(); // ok!
75 use std::cell::RefCell;
77 #[derive(Clone, Copy)] // we implement the Copy trait
81 fn nothing_is_true(self) {}
85 let x = RefCell::new(TheDarkKnight);
87 x.borrow().nothing_is_true(); // ok!
91 Moving a member out of a mutably borrowed struct will also cause E0507 error:
97 fn nothing_is_true(self) {}
101 knight: TheDarkKnight
105 let mut cave = Batcave {
106 knight: TheDarkKnight
108 let borrowed = &mut cave;
110 borrowed.knight.nothing_is_true(); // E0507
114 It is fine only if you put something back. `mem::replace` can be used for that:
117 # struct TheDarkKnight;
118 # impl TheDarkKnight { fn nothing_is_true(self) {} }
119 # struct Batcave { knight: TheDarkKnight }
122 let mut cave = Batcave {
123 knight: TheDarkKnight
125 let borrowed = &mut cave;
127 mem::replace(&mut borrowed.knight, TheDarkKnight).nothing_is_true(); // ok!
130 You can find more information about borrowing in the rust-book:
131 http://doc.rust-lang.org/book/ch04-02-references-and-borrowing.html