diff --git a/exercises/standard_library_types/rc1.rs b/exercises/standard_library_types/rc1.rs new file mode 100644 index 00000000..9b907fde --- /dev/null +++ b/exercises/standard_library_types/rc1.rs @@ -0,0 +1,98 @@ +// rc1.rs +// In this exercise, we want to express the concept of multiple owners via the Rc type. +// This is a model of our solar system - there is a Sun type and multiple Planets. +// The Planets take ownership of the sun, indicating that they revolve around the sun. + +// Make this code compile by using the proper Rc primitives to express that the sun has multiple owners. + +// I AM NOT DONE +use std::rc::Rc; + +#[derive(Debug)] +struct Sun {} + +#[derive(Debug)] +enum Planet { + Mercury(Rc), + Venus(Rc), + Earth(Rc), + Mars(Rc), + Jupiter(Rc), + Saturn(Rc), + Uranus(Rc), + Neptune(Rc), +} + +impl Planet { + fn details(&self) { + println!("Hi from {:?}!", self) + } +} + +fn main() { + let sun = Rc::new(Sun {}); + println!("reference count = {}", Rc::strong_count(&sun)); // 1 reference + + let mercury = Planet::Mercury(Rc::clone(&sun)); + println!("reference count = {}", Rc::strong_count(&sun)); // 2 references + mercury.details(); + + let venus = Planet::Venus(Rc::clone(&sun)); + println!("reference count = {}", Rc::strong_count(&sun)); // 3 references + venus.details(); + + let earth = Planet::Earth(Rc::clone(&sun)); + println!("reference count = {}", Rc::strong_count(&sun)); // 4 references + earth.details(); + + let mars = Planet::Mars(Rc::clone(&sun)); + println!("reference count = {}", Rc::strong_count(&sun)); // 5 references + mars.details(); + + let jupiter = Planet::Jupiter(Rc::clone(&sun)); + println!("reference count = {}", Rc::strong_count(&sun)); // 6 references + jupiter.details(); + + // TODO + let saturn = Planet::Saturn(Rc::new(Sun {})); + println!("reference count = {}", Rc::strong_count(&sun)); // 7 references + saturn.details(); + + // TODO + let uranus = Planet::Uranus(Rc::new(Sun {})); + println!("reference count = {}", Rc::strong_count(&sun)); // 8 references + uranus.details(); + + // TODO + let neptune = Planet::Neptune(Rc::new(Sun {})); + println!("reference count = {}", Rc::strong_count(&sun)); // 9 references + neptune.details(); + + assert_eq!(Rc::strong_count(&sun), 9); + + drop(neptune); + println!("reference count = {}", Rc::strong_count(&sun)); // 8 references + + drop(uranus); + println!("reference count = {}", Rc::strong_count(&sun)); // 7 references + + drop(saturn); + println!("reference count = {}", Rc::strong_count(&sun)); // 6 references + + drop(jupiter); + println!("reference count = {}", Rc::strong_count(&sun)); // 5 references + + drop(mars); + println!("reference count = {}", Rc::strong_count(&sun)); // 4 references + + // TODO + println!("reference count = {}", Rc::strong_count(&sun)); // 3 references + + // TODO + println!("reference count = {}", Rc::strong_count(&sun)); // 2 references + + // TODO + println!("reference count = {}", Rc::strong_count(&sun)); // 1 reference + + assert_eq!(Rc::strong_count(&sun), 1); +} diff --git a/info.toml b/info.toml index 5b7b9b43..a72c0147 100644 --- a/info.toml +++ b/info.toml @@ -929,6 +929,20 @@ is too much of a struggle, consider reading through all of Chapter 16 in the boo https://doc.rust-lang.org/stable/book/ch16-00-concurrency.html """ +[[exercises]] +name = "rc1" +path = "exercises/standard_library_types/rc1.rs" +mode = "compile" +hint = """ +This is a straightforward exercise to use the Rc type. Each Planet has +ownership of the Sun, and uses Rc::clone() to increment the reference count of the Sun. +After using drop() to move the Planets out of scope individually, the reference count goes down. +In the end the sun only has one reference again, to itself. See more at: +https://doc.rust-lang.org/book/ch15-04-rc.html + +* Unforunately Pluto is no longer considered a planet :( +""" + # THREADS [[exercises]]