X-Git-Url: https://git.ralfj.de/rust-101.git/blobdiff_plain/188b1ec1b8528e2326791feccc8077e15bd60182..7fdd4203f19f2fa9096d0a662acf22d447e57af1:/src/part12.rs?ds=inline diff --git a/src/part12.rs b/src/part12.rs index c749865..d5b7ce3 100644 --- a/src/part12.rs +++ b/src/part12.rs @@ -9,6 +9,7 @@ use std::cell::{Cell, RefCell}; //@ (There's not even an automatic derivation happening for the cases where it would be possible.) //@ This restriction propagates up to `Callbacks` itself. What could we do about this? +//@ ## `Rc` //@ The solution is to find some way of cloning `Callbacks` without cloning the environments. This can be achieved with //@ `Rc`, a *reference-counted* pointer. This is is another example of a smart pointer. You can `clone` an `Rc` as often //@ as you want, that doesn't affect the data it contains. It only creates more references to the same data. Once all the @@ -26,7 +27,7 @@ struct Callbacks { impl Callbacks { pub fn new() -> Self { - Callbacks { callbacks: Vec::new() } /*@*/ + Callbacks { callbacks: Vec::new() } } // Registration works just like last time, except that we are creating an `Rc` now. @@ -37,7 +38,7 @@ impl Callbacks { pub fn call(&self, val: i32) { // We only need a shared iterator here. Since `Rc` is a smart pointer, we can directly call the callback. for callback in self.callbacks.iter() { - callback(val); /*@*/ + callback(val); /*@*/ } } } @@ -108,11 +109,11 @@ struct CallbacksMut { impl CallbacksMut { pub fn new() -> Self { - CallbacksMut { callbacks: Vec::new() } /*@*/ + CallbacksMut { callbacks: Vec::new() } } pub fn register(&mut self, callback: F) { - let cell = Rc::new(RefCell::new(callback)); + let cell = Rc::new(RefCell::new(callback)); /*@*/ self.callbacks.push(cell); /*@*/ }