From 7479a4737bdcac347322ad0883ca528c8675e720 Mon Sep 17 00:00:00 2001 From: AlexandruGG Date: Tue, 26 May 2020 21:46:24 +0100 Subject: [PATCH 1/7] feat: Add box1.rs exercise --- exercises/standard_library_types/README.md | 2 ++ exercises/standard_library_types/box1.rs | 35 ++++++++++++++++++++++ info.toml | 18 +++++++++++ 3 files changed, 55 insertions(+) create mode 100644 exercises/standard_library_types/box1.rs diff --git a/exercises/standard_library_types/README.md b/exercises/standard_library_types/README.md index d138d874..36b30c1f 100644 --- a/exercises/standard_library_types/README.md +++ b/exercises/standard_library_types/README.md @@ -1,3 +1,5 @@ +For the Box exercise check out the chapter [Using Box to Point to Data on the Heap](https://doc.rust-lang.org/book/ch15-01-box.html). + For the Arc exercise check out the chapter [Shared-State Concurrency](https://doc.rust-lang.org/book/ch16-03-shared-state.html) of the Rust Book. For the Iterator exercise check out the chapters [Iterator](https://doc.rust-lang.org/book/ch13-02-iterators.html) of the Rust Book and the [Iterator documentation](https://doc.rust-lang.org/stable/std/iter/). diff --git a/exercises/standard_library_types/box1.rs b/exercises/standard_library_types/box1.rs new file mode 100644 index 00000000..11156ea0 --- /dev/null +++ b/exercises/standard_library_types/box1.rs @@ -0,0 +1,35 @@ +// box1.rs +// +// At compile time, Rust needs to know how much space a type takes up. This becomes problematic +// for recursive types, where a value can have as part of itself another value of the same type. +// To get around the issue, we can use a `Box` - a smart pointer used to store data on the heap, +// which also allows us to wrap a recursive type. +// +// The recursive type we're implementing in this exercise is the `cons list` - a data structure +// frequently found in functional programming languages. Each item in a cons list contains two +// elements: the value of the current item and the next item. The last item is a value called `Nil`. +// +// Step 1: use a `Box` in the enum definition to make the code compile +// Step 2: create both empty and non-empty cons lists of by replacing `unimplemented!()` +// +// Execute `rustlings hint box1` for hints :) + +// I AM NOT DONE + +#[derive(PartialEq, Debug)] +enum List { + Cons(i32, List), + Nil, +} + +fn main() { + let empty_list = unimplemented!(); + println!("This is an empty cons list: {:?}", empty_list); + + let non_empty_list = unimplemented!(); + println!("This is a non-empty cons list: {:?}", non_empty_list); + + // Do not change these + assert_eq!(List::Nil, empty_list); + assert_ne!(empty_list, non_empty_list); +} diff --git a/info.toml b/info.toml index e2aa82a7..dcd93bf2 100644 --- a/info.toml +++ b/info.toml @@ -614,6 +614,24 @@ hint = """ # STANDARD LIBRARY TYPES +[[exercises]] +name = "box1" +path = "exercises/standard_library_types/box1.rs" +mode = "compile" +hint = """ +Step 1 +The compiler's message should help: since we cannot store the value of the actual type +when working with recursive types, we need to store a reference (pointer) to its value. +We should therefore place our `List` inside a `Box`. More details in the book here: +https://doc.rust-lang.org/book/ch15-01-box.html#enabling-recursive-types-with-boxes + +Step 2 +Creating an empty list should be fairly straightforward (hint: peek at the assertions). +For a non-empty list keep in mind that wee want to use our Cons "list builder". +Although the current list is one of integers (i32), feel free to change the definition +and try other types! +""" + [[exercises]] name = "arc1" path = "exercises/standard_library_types/arc1.rs" From df81141d6fb3f43a7a035c4efc1150b6ede0b472 Mon Sep 17 00:00:00 2001 From: AlexandruGG Date: Wed, 27 May 2020 10:03:59 +0100 Subject: [PATCH 2/7] Address PR feedback: add tests --- exercises/standard_library_types/box1.rs | 38 +++++++++++++++++------- info.toml | 6 ++-- 2 files changed, 31 insertions(+), 13 deletions(-) diff --git a/exercises/standard_library_types/box1.rs b/exercises/standard_library_types/box1.rs index 11156ea0..2248962e 100644 --- a/exercises/standard_library_types/box1.rs +++ b/exercises/standard_library_types/box1.rs @@ -12,24 +12,42 @@ // Step 1: use a `Box` in the enum definition to make the code compile // Step 2: create both empty and non-empty cons lists of by replacing `unimplemented!()` // +// Note: the tests should not be changed +// // Execute `rustlings hint box1` for hints :) // I AM NOT DONE #[derive(PartialEq, Debug)] -enum List { +pub enum List { Cons(i32, List), Nil, } fn main() { - let empty_list = unimplemented!(); - println!("This is an empty cons list: {:?}", empty_list); - - let non_empty_list = unimplemented!(); - println!("This is a non-empty cons list: {:?}", non_empty_list); - - // Do not change these - assert_eq!(List::Nil, empty_list); - assert_ne!(empty_list, non_empty_list); + println!("This is an empty cons list: {:?}", create_empty_list()); + println!("This is a non-empty cons list: {:?}", create_non_empty_list()); +} + +pub fn create_empty_list() -> List { + unimplemented!() +} + +pub fn create_non_empty_list() -> List { + unimplemented!() +} + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn test_create_empty_list() { + assert_eq!(List::Nil, create_empty_list()) + } + + #[test] + fn test_create_non_empty_list() { + assert_ne!(create_empty_list(), create_non_empty_list()) + } } diff --git a/info.toml b/info.toml index dcd93bf2..842253c5 100644 --- a/info.toml +++ b/info.toml @@ -617,17 +617,17 @@ hint = """ [[exercises]] name = "box1" path = "exercises/standard_library_types/box1.rs" -mode = "compile" +mode = "test" hint = """ Step 1 The compiler's message should help: since we cannot store the value of the actual type when working with recursive types, we need to store a reference (pointer) to its value. -We should therefore place our `List` inside a `Box`. More details in the book here: +We should, therefore, place our `List` inside a `Box`. More details in the book here: https://doc.rust-lang.org/book/ch15-01-box.html#enabling-recursive-types-with-boxes Step 2 Creating an empty list should be fairly straightforward (hint: peek at the assertions). -For a non-empty list keep in mind that wee want to use our Cons "list builder". +For a non-empty list keep in mind that we want to use our Cons "list builder". Although the current list is one of integers (i32), feel free to change the definition and try other types! """ From 7e79c512225eb2a302db7f9b041c736b806e97f4 Mon Sep 17 00:00:00 2001 From: AlexandruGG Date: Thu, 28 May 2020 18:01:32 +0100 Subject: [PATCH 3/7] Add .idea to gitignore --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index de87c1e7..6094e5c1 100644 --- a/.gitignore +++ b/.gitignore @@ -5,3 +5,4 @@ target/ *.pdb exercises/clippy/Cargo.toml exercises/clippy/Cargo.lock +.idea From 173bb14140c5530cbdb59e53ace3991a99d804af Mon Sep 17 00:00:00 2001 From: Dan Wilhelm Date: Thu, 28 May 2020 20:21:33 -0700 Subject: [PATCH 4/7] feat: Add traits README --- exercises/traits/README.md | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) create mode 100644 exercises/traits/README.md diff --git a/exercises/traits/README.md b/exercises/traits/README.md new file mode 100644 index 00000000..1ce46fe0 --- /dev/null +++ b/exercises/traits/README.md @@ -0,0 +1,20 @@ +### Traits + +A trait is a collection of methods. + +Data types can implement traits. To do so, the methods making up the trait are defined for the data type. For example, the `String` data type implements the `From<&str>` trait. This allows a user to write `String::from("hello")`. + +In this way, traits are somewhat similar to Java interfaces and C++ abstract classes. + +Some additional common Rust traits include: + ++ `Clone` (the `clone` method), ++ `Display` (which allows formatted display via `{}`), and ++ `Debug` (which allows formatted display via `{:?}`). + +Because traits indicate shared behavior between data types, they are useful when writing generics. + + +#### Book Sections + +- [Traits](https://doc.rust-lang.org/book/ch10-02-traits.html) \ No newline at end of file From 524e17df10db95f7b90a0f75cc8997182a8a4094 Mon Sep 17 00:00:00 2001 From: Alexx Roche Date: Wed, 3 Jun 2020 13:34:43 +0200 Subject: [PATCH 5/7] fix(variables6): minor typo (#419) Looks like this was cloned from variables5.rs --- exercises/variables/variables6.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/exercises/variables/variables6.rs b/exercises/variables/variables6.rs index 76afa859..98666914 100644 --- a/exercises/variables/variables6.rs +++ b/exercises/variables/variables6.rs @@ -1,4 +1,4 @@ -// variables5.rs +// variables6.rs // Make me compile! Execute the command `rustlings hint variables6` if you want a hint :) // I AM NOT DONE From 5563adbb890587fc48fbbc9c4028642687f1e85b Mon Sep 17 00:00:00 2001 From: Alexx Roche Date: Wed, 3 Jun 2020 20:06:35 +0200 Subject: [PATCH 6/7] fix: fix quiz naming inconsistency (#421) Inconsistent naming when compared with the other quiz files. --- exercises/quiz3.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/exercises/quiz3.rs b/exercises/quiz3.rs index 30596b9b..a0cd3712 100644 --- a/exercises/quiz3.rs +++ b/exercises/quiz3.rs @@ -1,4 +1,4 @@ -// quiz.rs +// quiz3.rs // This is a quiz for the following sections: // - Tests From 0dd1c6ca6b389789e0972aa955fe17aa15c95f29 Mon Sep 17 00:00:00 2001 From: Alexx Roche Date: Wed, 3 Jun 2020 20:07:06 +0200 Subject: [PATCH 7/7] fix: rename quiz1 to tests1 in info (#420) `rustlings run tests1` wasn't working because of this typo. --- info.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/info.toml b/info.toml index d2c2ba50..2c871ad2 100644 --- a/info.toml +++ b/info.toml @@ -311,7 +311,7 @@ hint = "No hints this time ;)" # TESTS [[exercises]] -name = "quiz1" +name = "tests1" path = "exercises/tests/tests1.rs" mode = "test" hint = """