mirror of
https://github.com/rust-lang/rustlings.git
synced 2026-01-03 17:29:18 +00:00
Pending changes exported from your codespace
This commit is contained in:
parent
07e60302dd
commit
cc380ef209
@ -13,7 +13,7 @@
|
||||
// Execute `rustlings hint intro1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
|
||||
fn main() {
|
||||
println!("Hello and");
|
||||
|
||||
@ -5,8 +5,8 @@
|
||||
// Execute `rustlings hint intro2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
|
||||
fn main() {
|
||||
printline!("Hello there!")
|
||||
println!("Hello there!")
|
||||
}
|
||||
|
||||
@ -5,9 +5,8 @@
|
||||
// Execute `rustlings hint variables1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
x = 5;
|
||||
let x = 5;
|
||||
println!("x has the value {}", x);
|
||||
}
|
||||
|
||||
@ -3,10 +3,9 @@
|
||||
// Execute `rustlings hint variables2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let x;
|
||||
let x:u32 =0;
|
||||
if x == 10 {
|
||||
println!("x is ten!");
|
||||
} else {
|
||||
|
||||
@ -3,9 +3,8 @@
|
||||
// Execute `rustlings hint variables3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let x: i32;
|
||||
let x: i32=0;
|
||||
println!("Number {}", x);
|
||||
}
|
||||
|
||||
@ -3,10 +3,9 @@
|
||||
// Execute `rustlings hint variables4` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let x = 3;
|
||||
let mut x = 3;
|
||||
println!("Number {}", x);
|
||||
x = 5; // don't change this line
|
||||
println!("Number {}", x);
|
||||
|
||||
@ -3,11 +3,10 @@
|
||||
// Execute `rustlings hint variables5` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let number = "T-H-R-E-E"; // don't change this line
|
||||
println!("Spell a Number : {}", number);
|
||||
number = 3; // don't rename this variable
|
||||
let number = 3; // don't rename this variable
|
||||
println!("Number plus two is : {}", number + 2);
|
||||
}
|
||||
|
||||
@ -3,9 +3,8 @@
|
||||
// Execute `rustlings hint variables6` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
const NUMBER = 3;
|
||||
const NUMBER:u32 = 3;
|
||||
fn main() {
|
||||
println!("Number {}", NUMBER);
|
||||
}
|
||||
|
||||
@ -3,8 +3,7 @@
|
||||
// Execute `rustlings hint functions1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
call_me();
|
||||
|
||||
}
|
||||
|
||||
@ -3,13 +3,12 @@
|
||||
// Execute `rustlings hint functions2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
call_me(3);
|
||||
}
|
||||
|
||||
fn call_me(num:) {
|
||||
fn call_me(num: i32) {
|
||||
for i in 0..num {
|
||||
println!("Ring! Call number {}", i + 1);
|
||||
}
|
||||
|
||||
@ -3,10 +3,9 @@
|
||||
// Execute `rustlings hint functions3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
call_me();
|
||||
call_me(4);
|
||||
}
|
||||
|
||||
fn call_me(num: u32) {
|
||||
|
||||
@ -8,14 +8,13 @@
|
||||
// Execute `rustlings hint functions4` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let original_price = 51;
|
||||
println!("Your sale price is {}", sale_price(original_price));
|
||||
}
|
||||
|
||||
fn sale_price(price: i32) -> {
|
||||
fn sale_price(price: i32) -> i32{
|
||||
if is_even(price) {
|
||||
price - 10
|
||||
} else {
|
||||
|
||||
@ -3,13 +3,13 @@
|
||||
// Execute `rustlings hint functions5` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn square(num: i32) -> i32 {
|
||||
num * num
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let answer = square(3);
|
||||
println!("The square of 3 is {}", answer);
|
||||
}
|
||||
|
||||
fn square(num: i32) -> i32 {
|
||||
num * num;
|
||||
}
|
||||
|
||||
@ -2,13 +2,18 @@
|
||||
//
|
||||
// Execute `rustlings hint if1` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub fn bigger(a: i32, b: i32) -> i32 {
|
||||
// Complete this function to return the bigger number!
|
||||
// Do not use:
|
||||
// - another function call
|
||||
// - additional variables
|
||||
|
||||
if a > b {
|
||||
a
|
||||
} else {
|
||||
b
|
||||
}
|
||||
}
|
||||
|
||||
// Don't mind this for now :)
|
||||
|
||||
@ -5,13 +5,14 @@
|
||||
//
|
||||
// Execute `rustlings hint if2` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub fn foo_if_fizz(fizzish: &str) -> &str {
|
||||
if fizzish == "fizz" {
|
||||
"foo"
|
||||
} else if fizzish == "fuzz" {
|
||||
"bar"
|
||||
} else {
|
||||
1
|
||||
"baz"
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -2,19 +2,29 @@
|
||||
//
|
||||
// Execute `rustlings hint if3` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub fn animal_habitat(animal: &str) -> &'static str {
|
||||
let identifier = if animal == "crab" {
|
||||
1
|
||||
} else if animal == "gopher" {
|
||||
2.0
|
||||
2
|
||||
} else if animal == "snake" {
|
||||
3
|
||||
} else {
|
||||
"Unknown"
|
||||
4
|
||||
};
|
||||
|
||||
/// The value of `identifier` can be either an integer or a string.
|
||||
/// If `animal` is "crab", the value is 1.
|
||||
/// If `animal` is "gopher", the value is 2.0.
|
||||
/// If `animal` is "snake", the value is 3.
|
||||
/// Otherwise, the value is "Unknown".
|
||||
///
|
||||
/// The type `&'static str` represents a string slice that has a static lifetime,
|
||||
/// meaning it is available for the entire duration of the program.
|
||||
/// In this case, it represents a string literal that will be stored in the program's
|
||||
/// binary and can be safely referenced for the entire program's execution.
|
||||
|
||||
// DO NOT CHANGE THIS STATEMENT BELOW
|
||||
let habitat = if identifier == 1 {
|
||||
"Beach"
|
||||
|
||||
@ -3,7 +3,6 @@
|
||||
// Fill in the rest of the line that has code missing! No hints, there's no
|
||||
// tricks, just get used to typing these :)
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
// Booleans (`bool`)
|
||||
@ -13,7 +12,7 @@ fn main() {
|
||||
println!("Good morning!");
|
||||
}
|
||||
|
||||
let // Finish the rest of this line like the example! Or make it be false!
|
||||
let is_evening:bool =false;// Finish the rest of this line like the example! Or make it be false!
|
||||
if is_evening {
|
||||
println!("Good evening!");
|
||||
}
|
||||
|
||||
@ -3,7 +3,6 @@
|
||||
// Fill in the rest of the line that has code missing! No hints, there's no
|
||||
// tricks, just get used to typing these :)
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
// Characters (`char`)
|
||||
@ -19,7 +18,8 @@ fn main() {
|
||||
println!("Neither alphabetic nor numeric!");
|
||||
}
|
||||
|
||||
let // Finish this line like the example! What's your favorite character?
|
||||
let your_character = '👻';
|
||||
// Finish this line like the example! What's your favorite character?
|
||||
// Try a letter, try a number, try a special character, try a character
|
||||
// from a different language than your own, try an emoji!
|
||||
if your_character.is_alphabetic() {
|
||||
|
||||
@ -5,10 +5,9 @@
|
||||
// Execute `rustlings hint primitive_types3` or use the `hint` watch subcommand
|
||||
// for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let a = ???
|
||||
let a = [0; 100];
|
||||
|
||||
if a.len() >= 100 {
|
||||
println!("Wow, that's a big array!");
|
||||
|
||||
@ -5,13 +5,12 @@
|
||||
// Execute `rustlings hint primitive_types4` or use the `hint` watch subcommand
|
||||
// for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[test]
|
||||
fn slice_out_of_array() {
|
||||
let a = [1, 2, 3, 4, 5];
|
||||
|
||||
let nice_slice = ???
|
||||
|
||||
let nice_slice = &a[1..4];
|
||||
//in python this would be a[1:4]
|
||||
assert_eq!([2, 3, 4], nice_slice)
|
||||
}
|
||||
|
||||
@ -5,11 +5,10 @@
|
||||
// Execute `rustlings hint primitive_types5` or use the `hint` watch subcommand
|
||||
// for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let cat = ("Furry McFurson", 3.5);
|
||||
let /* your pattern here */ = cat;
|
||||
let (name,age)/* your pattern here */ = cat;
|
||||
|
||||
println!("{} is {} years old.", name, age);
|
||||
}
|
||||
|
||||
@ -6,13 +6,12 @@
|
||||
// Execute `rustlings hint primitive_types6` or use the `hint` watch subcommand
|
||||
// for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[test]
|
||||
fn indexing_tuple() {
|
||||
let numbers = (1, 2, 3);
|
||||
// Replace below ??? with the tuple indexing syntax.
|
||||
let second = ???;
|
||||
let second = numbers.1;
|
||||
|
||||
assert_eq!(2, second,
|
||||
"This is not the 2nd number in the tuple!")
|
||||
|
||||
@ -7,11 +7,13 @@
|
||||
//
|
||||
// Execute `rustlings hint vecs1` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn array_and_vec() -> ([i32; 4], Vec<i32>) {
|
||||
let a = [10, 20, 30, 40]; // a plain array
|
||||
let v = // TODO: declare your vector here with the macro for vectors
|
||||
// let v :Vec<[i32; 4]> =vec![a]; // TODO: declare your vector here with the macro for vectors
|
||||
// let v = vec![10, 20, 30, 40]; // declare your vector here with the macro for vectors
|
||||
|
||||
let v =Vec::from(a); // TODO: declare your vector here with the macro for vectors
|
||||
|
||||
(a, v)
|
||||
}
|
||||
@ -26,3 +28,4 @@ mod tests {
|
||||
assert_eq!(a, v[..]);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -7,13 +7,13 @@
|
||||
//
|
||||
// Execute `rustlings hint vecs2` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn vec_loop(mut v: Vec<i32>) -> Vec<i32> {
|
||||
for element in v.iter_mut() {
|
||||
// TODO: Fill this up so that each element in the Vec `v` is
|
||||
// multiplied by 2.
|
||||
???
|
||||
|
||||
*element *= 2;
|
||||
}
|
||||
|
||||
// At this point, `v` should be equal to [4, 8, 12, 16, 20].
|
||||
@ -24,7 +24,8 @@ fn vec_map(v: &Vec<i32>) -> Vec<i32> {
|
||||
v.iter().map(|element| {
|
||||
// TODO: Do the same thing as above - but instead of mutating the
|
||||
// Vec, you can just return the new number!
|
||||
???
|
||||
|
||||
element * 2
|
||||
}).collect()
|
||||
}
|
||||
|
||||
|
||||
@ -3,7 +3,6 @@
|
||||
// Execute `rustlings hint move_semantics1` or use the `hint` watch subcommand
|
||||
// for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[test]
|
||||
fn main() {
|
||||
@ -15,7 +14,7 @@ fn main() {
|
||||
}
|
||||
|
||||
fn fill_vec(vec: Vec<i32>) -> Vec<i32> {
|
||||
let vec = vec;
|
||||
let mut vec = vec;
|
||||
|
||||
vec.push(88);
|
||||
|
||||
|
||||
@ -5,20 +5,19 @@
|
||||
// Execute `rustlings hint move_semantics2` or use the `hint` watch subcommand
|
||||
// for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[test]
|
||||
fn main() {
|
||||
let vec0 = vec![22, 44, 66];
|
||||
|
||||
let mut vec1 = fill_vec(vec0);
|
||||
let mut vec1 = fill_vec(&vec0);
|
||||
|
||||
assert_eq!(vec0, vec![22, 44, 66]);
|
||||
assert_eq!(vec1, vec![22, 44, 66, 88]);
|
||||
}
|
||||
|
||||
fn fill_vec(vec: Vec<i32>) -> Vec<i32> {
|
||||
let mut vec = vec;
|
||||
fn fill_vec(vec: &Vec<i32>) -> Vec<i32> {
|
||||
let mut vec = vec.clone();
|
||||
|
||||
vec.push(88);
|
||||
|
||||
|
||||
@ -6,7 +6,6 @@
|
||||
// Execute `rustlings hint move_semantics3` or use the `hint` watch subcommand
|
||||
// for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[test]
|
||||
fn main() {
|
||||
@ -17,7 +16,7 @@ fn main() {
|
||||
assert_eq!(vec1, vec![22, 44, 66, 88]);
|
||||
}
|
||||
|
||||
fn fill_vec(vec: Vec<i32>) -> Vec<i32> {
|
||||
fn fill_vec(mut vec: Vec<i32>) -> Vec<i32> {
|
||||
vec.push(88);
|
||||
|
||||
vec
|
||||
|
||||
@ -7,13 +7,12 @@
|
||||
// Execute `rustlings hint move_semantics4` or use the `hint` watch subcommand
|
||||
// for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[test]
|
||||
fn main() {
|
||||
let vec0 = vec![22, 44, 66];
|
||||
|
||||
|
||||
let mut vec1 = fill_vec(vec0);
|
||||
let mut vec1 = fill_vec();
|
||||
|
||||
assert_eq!(vec1, vec![22, 44, 66, 88]);
|
||||
}
|
||||
@ -21,6 +20,7 @@ fn main() {
|
||||
// `fill_vec()` no longer takes `vec: Vec<i32>` as argument - don't change this!
|
||||
fn fill_vec() -> Vec<i32> {
|
||||
// Instead, let's create and fill the Vec in here - how do you do that?
|
||||
let vec = vec![22, 44, 66];
|
||||
let mut vec = vec;
|
||||
|
||||
vec.push(88);
|
||||
|
||||
@ -6,14 +6,13 @@
|
||||
// Execute `rustlings hint move_semantics5` or use the `hint` watch subcommand
|
||||
// for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[test]
|
||||
fn main() {
|
||||
let mut x = 100;
|
||||
let y = &mut x;
|
||||
let z = &mut x;
|
||||
*y += 100;
|
||||
let z = &mut x;
|
||||
*z += 1000;
|
||||
assert_eq!(x, 1200);
|
||||
}
|
||||
|
||||
@ -5,24 +5,23 @@
|
||||
// Execute `rustlings hint move_semantics6` or use the `hint` watch subcommand
|
||||
// for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let data = "Rust is great!".to_string();
|
||||
|
||||
get_char(data);
|
||||
get_char(&data);
|
||||
|
||||
string_uppercase(&data);
|
||||
string_uppercase(data);
|
||||
}
|
||||
|
||||
// Should not take ownership
|
||||
fn get_char(data: String) -> char {
|
||||
fn get_char(data: &String) -> char {
|
||||
data.chars().last().unwrap()
|
||||
}
|
||||
|
||||
// Should take ownership
|
||||
fn string_uppercase(mut data: &String) {
|
||||
data = &data.to_uppercase();
|
||||
fn string_uppercase(mut data: String) {
|
||||
data = data.to_uppercase();
|
||||
|
||||
println!("{}", data);
|
||||
}
|
||||
|
||||
@ -5,13 +5,14 @@
|
||||
// Execute `rustlings hint structs1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
struct ColorClassicStruct {
|
||||
// TODO: Something goes here
|
||||
red: u8,
|
||||
green: u8,
|
||||
blue: u8,
|
||||
}
|
||||
|
||||
struct ColorTupleStruct(/* TODO: Something goes here */);
|
||||
struct ColorTupleStruct(u8, u8, u8);
|
||||
|
||||
#[derive(Debug)]
|
||||
struct UnitLikeStruct;
|
||||
@ -22,8 +23,11 @@ mod tests {
|
||||
|
||||
#[test]
|
||||
fn classic_c_structs() {
|
||||
// TODO: Instantiate a classic c struct!
|
||||
// let green =
|
||||
let green = ColorClassicStruct {
|
||||
red: 0,
|
||||
green: 255,
|
||||
blue: 0,
|
||||
};
|
||||
|
||||
assert_eq!(green.red, 0);
|
||||
assert_eq!(green.green, 255);
|
||||
@ -32,8 +36,7 @@ mod tests {
|
||||
|
||||
#[test]
|
||||
fn tuple_structs() {
|
||||
// TODO: Instantiate a tuple struct!
|
||||
// let green =
|
||||
let green = ColorTupleStruct(0, 255, 0);
|
||||
|
||||
assert_eq!(green.0, 0);
|
||||
assert_eq!(green.1, 255);
|
||||
@ -42,8 +45,7 @@ mod tests {
|
||||
|
||||
#[test]
|
||||
fn unit_structs() {
|
||||
// TODO: Instantiate a unit-like struct!
|
||||
// let unit_like_struct =
|
||||
let unit_like_struct = UnitLikeStruct;
|
||||
let message = format!("{:?}s are fun!", unit_like_struct);
|
||||
|
||||
assert_eq!(message, "UnitLikeStructs are fun!");
|
||||
|
||||
@ -5,7 +5,6 @@
|
||||
// Execute `rustlings hint structs2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[derive(Debug)]
|
||||
struct Order {
|
||||
@ -39,6 +38,11 @@ mod tests {
|
||||
let order_template = create_order_template();
|
||||
// TODO: Create your own order using the update syntax and template above!
|
||||
// let your_order =
|
||||
let your_order = Order {
|
||||
name: String::from("Hacker in Rust"),
|
||||
count: 1,
|
||||
..order_template
|
||||
};
|
||||
assert_eq!(your_order.name, "Hacker in Rust");
|
||||
assert_eq!(your_order.year, order_template.year);
|
||||
assert_eq!(your_order.made_by_phone, order_template.made_by_phone);
|
||||
|
||||
@ -7,7 +7,6 @@
|
||||
// Execute `rustlings hint structs3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[derive(Debug)]
|
||||
struct Package {
|
||||
@ -31,12 +30,14 @@ impl Package {
|
||||
}
|
||||
}
|
||||
|
||||
fn is_international(&self) -> ??? {
|
||||
fn is_international(&self) -> bool {
|
||||
// Something goes here...
|
||||
self.sender_country != self.recipient_country
|
||||
}
|
||||
|
||||
fn get_fees(&self, cents_per_gram: u32) -> ??? {
|
||||
fn get_fees(&self, cents_per_gram: u32) -> u32 {
|
||||
// Something goes here...
|
||||
self.weight_in_grams * cents_per_gram
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -2,11 +2,14 @@
|
||||
//
|
||||
// No hints this time! ;)
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[derive(Debug)]
|
||||
enum Message {
|
||||
// TODO: define a few types of messages as used below
|
||||
Quit,
|
||||
Echo,
|
||||
Move,
|
||||
ChangeColor,
|
||||
}
|
||||
|
||||
fn main() {
|
||||
|
||||
@ -3,11 +3,14 @@
|
||||
// Execute `rustlings hint enums2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[derive(Debug)]
|
||||
enum Message {
|
||||
// TODO: define the different variants used below
|
||||
Move { x: i32, y: i32 },
|
||||
Echo(String),
|
||||
ChangeColor(i32, i32, i32),
|
||||
Quit,
|
||||
}
|
||||
|
||||
impl Message {
|
||||
|
||||
@ -5,10 +5,13 @@
|
||||
// Execute `rustlings hint enums3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
enum Message {
|
||||
// TODO: implement the message variant types based on their usage below
|
||||
ChangeColor(u8, u8, u8),
|
||||
Echo(String),
|
||||
Move(Point),
|
||||
Quit,
|
||||
}
|
||||
|
||||
struct Point {
|
||||
@ -43,6 +46,13 @@ impl State {
|
||||
fn process(&mut self, message: Message) {
|
||||
// TODO: create a match expression to process the different message variants
|
||||
// Remember: When passing a tuple as a function argument, you'll need extra parentheses:
|
||||
|
||||
match message {
|
||||
Message::ChangeColor(t, u, p) => self.change_color((t, u, p)),
|
||||
Message::Quit => self.quit(),
|
||||
Message::Echo(t) => self.echo(t),
|
||||
Message::Move(t) => self.move_position(t),
|
||||
}
|
||||
// fn function((t, u, p, l, e))
|
||||
}
|
||||
}
|
||||
|
||||
@ -5,7 +5,6 @@
|
||||
// Execute `rustlings hint strings1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let answer = current_favorite_color();
|
||||
@ -13,5 +12,5 @@ fn main() {
|
||||
}
|
||||
|
||||
fn current_favorite_color() -> String {
|
||||
"blue"
|
||||
"blue".to_string()
|
||||
}
|
||||
|
||||
@ -5,11 +5,12 @@
|
||||
// Execute `rustlings hint strings2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let word = String::from("green"); // Try not changing this line :)
|
||||
if is_a_color_word(word) {
|
||||
if is_a_color_word(&word //two ways in this line , i used Deref Coercion(Compiler findout what we need if Deref possible between the 2 types) to convert &String to &str
|
||||
/*word.as_str()*/ //here i used as_str() method directly to convert to &str
|
||||
) {
|
||||
println!("That is a color word I know!");
|
||||
} else {
|
||||
println!("That is not a color word I know.");
|
||||
|
||||
@ -3,21 +3,29 @@
|
||||
// Execute `rustlings hint strings3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn trim_me(input: &str) -> String {
|
||||
// TODO: Remove whitespace from both ends of a string!
|
||||
???
|
||||
input.trim().to_string()
|
||||
}
|
||||
|
||||
fn compose_me(input: &str) -> String {
|
||||
// TODO: Add " world!" to the string! There's multiple ways to do this!
|
||||
???
|
||||
// TODO: Add " world!" to the string! There's multiple ways to do this!
|
||||
|
||||
// 1. using format! macro
|
||||
format!("{} world!", input)
|
||||
// 2. using String::from() and push_str() method
|
||||
// let mut s = String::from(input);
|
||||
// s.push_str(" world!");
|
||||
// s
|
||||
// 3. using String::from() and + operator
|
||||
// let s = String::from(input) + " world!";
|
||||
// s
|
||||
}
|
||||
|
||||
fn replace_me(input: &str) -> String {
|
||||
// TODO: Replace "cars" in the string with "balloons"!
|
||||
???
|
||||
input.replace("cars", "balloons")
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
||||
@ -7,7 +7,6 @@
|
||||
//
|
||||
// No hints this time!
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn string_slice(arg: &str) {
|
||||
println!("{}", arg);
|
||||
@ -17,14 +16,14 @@ fn string(arg: String) {
|
||||
}
|
||||
|
||||
fn main() {
|
||||
???("blue");
|
||||
???("red".to_string());
|
||||
???(String::from("hi"));
|
||||
???("rust is fun!".to_owned());
|
||||
???("nice weather".into());
|
||||
???(format!("Interpolation {}", "Station"));
|
||||
???(&String::from("abc")[0..1]);
|
||||
???(" hello there ".trim());
|
||||
???("Happy Monday!".to_string().replace("Mon", "Tues"));
|
||||
???("mY sHiFt KeY iS sTiCkY".to_lowercase());
|
||||
string_slice("blue");
|
||||
string("red".to_string());
|
||||
string(String::from("hi"));
|
||||
string("rust is fun!".to_owned());
|
||||
string_slice("nice weather".into());
|
||||
string(format!("Interpolation {}", "Station"));
|
||||
string_slice(&String::from("abc")[0..1]);
|
||||
string_slice(" hello there ".trim());
|
||||
string("Happy Monday!".to_string().replace("Mon", "Tues"));
|
||||
string("mY sHiFt KeY iS sTiCkY".to_lowercase());
|
||||
}
|
||||
|
||||
@ -3,7 +3,6 @@
|
||||
// Execute `rustlings hint modules1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
mod sausage_factory {
|
||||
// Don't let anybody outside of this module see this!
|
||||
@ -11,7 +10,7 @@ mod sausage_factory {
|
||||
String::from("Ginger")
|
||||
}
|
||||
|
||||
fn make_sausage() {
|
||||
pub fn make_sausage() {
|
||||
get_secret_recipe();
|
||||
println!("sausage!");
|
||||
}
|
||||
|
||||
@ -7,12 +7,11 @@
|
||||
// Execute `rustlings hint modules2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
mod delicious_snacks {
|
||||
// TODO: Fix these use statements
|
||||
use self::fruits::PEAR as ???
|
||||
use self::veggies::CUCUMBER as ???
|
||||
pub use self::fruits::PEAR as fruit;
|
||||
pub use self::veggies::CUCUMBER as veggie;
|
||||
|
||||
mod fruits {
|
||||
pub const PEAR: &'static str = "Pear";
|
||||
|
||||
@ -8,10 +8,9 @@
|
||||
// Execute `rustlings hint modules3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
// TODO: Complete this use statement
|
||||
use ???
|
||||
use std::time::{SystemTime, UNIX_EPOCH};
|
||||
|
||||
fn main() {
|
||||
match SystemTime::now().duration_since(UNIX_EPOCH) {
|
||||
|
||||
@ -11,17 +11,18 @@
|
||||
// Execute `rustlings hint hashmaps1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::collections::HashMap;
|
||||
|
||||
fn fruit_basket() -> HashMap<String, u32> {
|
||||
let mut basket = // TODO: declare your hash map here.
|
||||
|
||||
let mut basket = HashMap::new();
|
||||
// TODO: declare your hash map here.
|
||||
// Two bananas are already given for you :)
|
||||
basket.insert(String::from("banana"), 2);
|
||||
|
||||
// TODO: Put more fruits in your basket here.
|
||||
basket.insert(String::from("apple"), 3);
|
||||
basket.insert(String::from("mango"), 4);
|
||||
|
||||
basket
|
||||
}
|
||||
|
||||
@ -14,7 +14,6 @@
|
||||
// Execute `rustlings hint hashmaps2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::collections::HashMap;
|
||||
|
||||
@ -40,6 +39,7 @@ fn fruit_basket(basket: &mut HashMap<Fruit, u32>) {
|
||||
// TODO: Insert new fruits if they are not already present in the
|
||||
// basket. Note that you are not allowed to put any type of fruit that's
|
||||
// already present!
|
||||
basket.entry(fruit).or_insert(1);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -14,7 +14,6 @@
|
||||
// Execute `rustlings hint hashmaps3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::collections::HashMap;
|
||||
|
||||
@ -29,7 +28,7 @@ fn build_scores_table(results: String) -> HashMap<String, Team> {
|
||||
let mut scores: HashMap<String, Team> = HashMap::new();
|
||||
|
||||
for r in results.lines() {
|
||||
let v: Vec<&str> = r.split(',').collect();
|
||||
let v:Vec<&str> = r.split(',').collect();
|
||||
let team_1_name = v[0].to_string();
|
||||
let team_1_score: u8 = v[2].parse().unwrap();
|
||||
let team_2_name = v[1].to_string();
|
||||
@ -39,6 +38,13 @@ fn build_scores_table(results: String) -> HashMap<String, Team> {
|
||||
// will be the number of goals conceded by team_2, and similarly
|
||||
// goals scored by team_2 will be the number of goals conceded by
|
||||
// team_1.
|
||||
let team_1 = scores.entry(team_1_name).or_insert(Team { goals_scored: 0, goals_conceded: 0 });
|
||||
team_1.goals_scored += team_1_score;
|
||||
team_1.goals_conceded += team_2_score;
|
||||
let team_2 = scores.entry(team_2_name).or_insert(Team { goals_scored: 0, goals_conceded: 0 });
|
||||
team_2.goals_scored += team_2_score;
|
||||
team_2.goals_conceded += team_1_score;
|
||||
|
||||
}
|
||||
scores
|
||||
}
|
||||
|
||||
@ -19,3 +19,16 @@ Option types are very common in Rust code, as they have a number of uses:
|
||||
- [Option Enum Documentation](https://doc.rust-lang.org/std/option/enum.Option.html)
|
||||
- [if let](https://doc.rust-lang.org/rust-by-example/flow_control/if_let.html)
|
||||
- [while let](https://doc.rust-lang.org/rust-by-example/flow_control/while_let.html)
|
||||
|
||||
|
||||
<!--
|
||||
quetsion mark operator usage along with option
|
||||
fn add_last_numbers(stack: &mut Vec<i32>) -> Option<i32> {
|
||||
Some(stack.pop()? + stack.pop()?)
|
||||
}
|
||||
Run
|
||||
It’s much nicer!
|
||||
|
||||
Ending the expression with ? will result in the Some’s unwrapped value, unless the result is None, in which case None is returned early from the enclosing function.
|
||||
|
||||
? can be used in functions that return Option because of the early return of None that it provides. -->
|
||||
@ -3,7 +3,8 @@
|
||||
// Execute `rustlings hint options1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use core::time;
|
||||
|
||||
// This function returns how much icecream there is left in the fridge.
|
||||
// If it's before 10PM, there's 5 pieces left. At 10PM, someone eats them
|
||||
@ -13,7 +14,20 @@ fn maybe_icecream(time_of_day: u16) -> Option<u16> {
|
||||
// value of 0 The Option output should gracefully handle cases where
|
||||
// time_of_day > 23.
|
||||
// TODO: Complete the function body - remember to return an Option!
|
||||
???
|
||||
match time_of_day {
|
||||
0..=21 => Some(5),
|
||||
22..=23 => Some(0),
|
||||
_ => None,
|
||||
}
|
||||
|
||||
// if time_of_day < 22 {
|
||||
// Some(5)
|
||||
// } else if time_of_day == 22 {
|
||||
// Some(0)
|
||||
// }
|
||||
// else if time_of_day > 23 {
|
||||
// None
|
||||
// }
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
@ -33,7 +47,9 @@ mod tests {
|
||||
fn raw_value() {
|
||||
// TODO: Fix this test. How do you get at the value contained in the
|
||||
// Option?
|
||||
let icecreams = maybe_icecream(12);
|
||||
|
||||
let icecreams = maybe_icecream(12).unwrap();
|
||||
|
||||
assert_eq!(icecreams, 5);
|
||||
}
|
||||
}
|
||||
|
||||
@ -3,17 +3,18 @@
|
||||
// Execute `rustlings hint options2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use std::iter::Flatten;
|
||||
|
||||
#[test]
|
||||
fn simple_option() {
|
||||
let target = "rustlings";
|
||||
let optional_target = Some(target);
|
||||
|
||||
// TODO: Make this an if let statement whose value is "Some" type
|
||||
word = optional_target {
|
||||
if let Some(word) = optional_target {
|
||||
assert_eq!(word, target);
|
||||
}
|
||||
}
|
||||
@ -32,7 +33,13 @@ mod tests {
|
||||
// TODO: make this a while let statement - remember that vector.pop also
|
||||
// adds another layer of Option<T>. You can stack `Option<T>`s into
|
||||
// while let and if let.
|
||||
integer = optional_integers.pop() {
|
||||
|
||||
//flatten is a method that takes a nested Option and returns an Option with the inner value
|
||||
//if the outer Option is Some and the inner Option is Some, it returns Some(inner value)
|
||||
//if the outer Option is Some and the inner Option is None, it returns None
|
||||
//if the outer Option is None, it returns None
|
||||
|
||||
while let Some(integer) = optional_integers.pop().flatten() {
|
||||
assert_eq!(integer, cursor);
|
||||
cursor -= 1;
|
||||
}
|
||||
|
||||
@ -3,7 +3,6 @@
|
||||
// Execute `rustlings hint options3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
struct Point {
|
||||
x: i32,
|
||||
@ -13,8 +12,21 @@ struct Point {
|
||||
fn main() {
|
||||
let y: Option<Point> = Some(Point { x: 100, y: 200 });
|
||||
|
||||
|
||||
|
||||
|
||||
// match y {
|
||||
// Some(p) => println!("Co-ordinates are {},{} ", p.x, p.y),
|
||||
// _ => panic!("no match!"),
|
||||
// }
|
||||
// y; // Fix without deleting this line.
|
||||
|
||||
// By default, match statements consume all they can, which can sometimes be a problem, when you don’t really need the value to be moved and owned: you just need to borrow it.
|
||||
// The ref keyword can be used to take references to the values in the pattern. This is useful when you want to match on a value, but don’t want to take ownership of it.
|
||||
// The ref keyword can be used in the pattern to take references to the values in the pattern. This is useful when you want to match on a value, but don’t want to take ownership of it.
|
||||
|
||||
match y {
|
||||
Some(p) => println!("Co-ordinates are {},{} ", p.x, p.y),
|
||||
Some(ref p) => println!("Co-ordinates are {},{} ", p.x, p.y),
|
||||
_ => panic!("no match!"),
|
||||
}
|
||||
y; // Fix without deleting this line.
|
||||
|
||||
@ -9,14 +9,15 @@
|
||||
// Execute `rustlings hint errors1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub fn generate_nametag_text(name: String) -> Option<String> {
|
||||
pub fn generate_nametag_text(name: String) -> Result<String,String> {
|
||||
if name.is_empty() {
|
||||
// Empty names aren't allowed.
|
||||
None
|
||||
// None
|
||||
Err("`name` was empty; it must be nonempty.".into())
|
||||
} else {
|
||||
Some(format!("Hi! My name is {}", name))
|
||||
// Some(format!("Hi! My name is {}", name))
|
||||
Ok(format!("Hi! My name is {}", name))
|
||||
}
|
||||
}
|
||||
|
||||
@ -27,7 +28,7 @@ mod tests {
|
||||
#[test]
|
||||
fn generates_nametag_text_for_a_nonempty_name() {
|
||||
assert_eq!(
|
||||
generate_nametag_text("Beyoncé".into()),
|
||||
generate_nametag_text("Beyoncé".into()),// into() is used to convert a string literal to a String
|
||||
Ok("Hi! My name is Beyoncé".into())
|
||||
);
|
||||
}
|
||||
|
||||
@ -19,16 +19,27 @@
|
||||
// Execute `rustlings hint errors2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::num::ParseIntError;
|
||||
|
||||
pub fn total_cost(item_quantity: &str) -> Result<i32, ParseIntError> {
|
||||
let processing_fee = 1;
|
||||
let cost_per_item = 5;
|
||||
let qty = item_quantity.parse::<i32>();
|
||||
// let qty = item_quantity.parse::<i32>()?;
|
||||
|
||||
Ok(qty * cost_per_item + processing_fee)
|
||||
// Ok(qty * cost_per_item + processing_fee)
|
||||
|
||||
//? is used to return the error if it exists/ This is the shorter way to implement the error handling.
|
||||
|
||||
|
||||
//The below code is the longer way to implement the error handling.
|
||||
let qty = item_quantity.parse::<i32>();
|
||||
match qty {
|
||||
Ok(qty) => Ok(qty * cost_per_item + processing_fee),
|
||||
Err(e) => Err(e),
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
||||
@ -7,11 +7,10 @@
|
||||
// Execute `rustlings hint errors3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::num::ParseIntError;
|
||||
|
||||
fn main() {
|
||||
fn main() -> Result<(), ParseIntError> {
|
||||
let mut tokens = 100;
|
||||
let pretend_user_input = "8";
|
||||
|
||||
@ -23,6 +22,9 @@ fn main() {
|
||||
tokens -= cost;
|
||||
println!("You now have {} tokens.", tokens);
|
||||
}
|
||||
|
||||
Ok(())// here we are returning the Ok() because the main function returns a Result type.
|
||||
|
||||
}
|
||||
|
||||
pub fn total_cost(item_quantity: &str) -> Result<i32, ParseIntError> {
|
||||
|
||||
@ -3,10 +3,9 @@
|
||||
// Execute `rustlings hint errors4` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[derive(PartialEq, Debug)]
|
||||
struct PositiveNonzeroInteger(u64);
|
||||
struct PositiveNonzeroInteger(u64);// used to store a positive non-zero integer , better for checking the error handling and better code readability.
|
||||
|
||||
#[derive(PartialEq, Debug)]
|
||||
enum CreationError {
|
||||
@ -17,7 +16,14 @@ enum CreationError {
|
||||
impl PositiveNonzeroInteger {
|
||||
fn new(value: i64) -> Result<PositiveNonzeroInteger, CreationError> {
|
||||
// Hmm... Why is this always returning an Ok value?
|
||||
Ok(PositiveNonzeroInteger(value as u64))
|
||||
// The value is always returning an Ok value because the value is always being converted to a positive integer.
|
||||
if value > 0 {
|
||||
Ok(PositiveNonzeroInteger(value as u64))
|
||||
} else if value == 0 {
|
||||
Err(CreationError::Zero)
|
||||
} else {
|
||||
Err(CreationError::Negative)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -22,14 +22,14 @@
|
||||
// Execute `rustlings hint errors5` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::error;
|
||||
use std::fmt;
|
||||
use std::num::ParseIntError;
|
||||
|
||||
|
||||
// TODO: update the return type of `main()` to make this compile.
|
||||
fn main() -> Result<(), Box<dyn ???>> {
|
||||
fn main() -> Result<(), Box<dyn error::Error>> {
|
||||
let pretend_user_input = "42";
|
||||
let x: i64 = pretend_user_input.parse()?;
|
||||
println!("output={:?}", PositiveNonzeroInteger::new(x)?);
|
||||
@ -68,4 +68,6 @@ impl fmt::Display for CreationError {
|
||||
}
|
||||
}
|
||||
|
||||
//Implementing fmt::Display for CreationError allows us to customize the formatting of the error message when it is displayed to the user. While error::Error provides a default implementation for displaying errors, it may not always provide the desired format or level of detail. By implementing fmt::Display, we have more control over how the error message is presented.
|
||||
|
||||
impl error::Error for CreationError {}
|
||||
|
||||
@ -9,8 +9,7 @@
|
||||
// Execute `rustlings hint errors6` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
// this was a good excercise to understand the error handling in rust.--- Macho Commented🫡
|
||||
use std::num::ParseIntError;
|
||||
|
||||
// This is a custom error type that we will be using in `parse_pos_nonzero()`.
|
||||
@ -20,19 +19,27 @@ enum ParsePosNonzeroError {
|
||||
ParseInt(ParseIntError),
|
||||
}
|
||||
|
||||
|
||||
impl ParsePosNonzeroError {
|
||||
fn from_creation(err: CreationError) -> ParsePosNonzeroError {
|
||||
ParsePosNonzeroError::Creation(err)
|
||||
}
|
||||
// TODO: add another error conversion function here.
|
||||
// fn from_parseint...
|
||||
fn from_parseint(err: ParseIntError) -> ParsePosNonzeroError {
|
||||
ParsePosNonzeroError::ParseInt(err)
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
fn parse_pos_nonzero(s: &str) -> Result<PositiveNonzeroInteger, ParsePosNonzeroError> {
|
||||
// TODO: change this to return an appropriate error instead of panicking
|
||||
// when `parse()` returns an error.
|
||||
let x: i64 = s.parse().unwrap();
|
||||
|
||||
|
||||
let x: i64 = s.parse().map_err(ParsePosNonzeroError::from_parseint)?; //? is used to return the error if it exists/ This is the shorter way to implement the error handling.;
|
||||
PositiveNonzeroInteger::new(x).map_err(ParsePosNonzeroError::from_creation)
|
||||
|
||||
|
||||
}
|
||||
|
||||
// Don't change anything below this line.
|
||||
|
||||
@ -6,9 +6,8 @@
|
||||
// Execute `rustlings hint generics1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
let mut shopping_list: Vec<?> = Vec::new();
|
||||
let mut shopping_list: Vec<&str> = Vec::new();
|
||||
shopping_list.push("milk");
|
||||
}
|
||||
|
||||
@ -6,14 +6,14 @@
|
||||
// Execute `rustlings hint generics2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
struct Wrapper {
|
||||
value: u32,
|
||||
struct Wrapper<T> {
|
||||
value: T,
|
||||
}
|
||||
|
||||
impl Wrapper {
|
||||
pub fn new(value: u32) -> Self {
|
||||
|
||||
impl <T> Wrapper <T>{
|
||||
pub fn new(value: T) -> Self {
|
||||
Wrapper { value }
|
||||
}
|
||||
}
|
||||
|
||||
@ -7,7 +7,6 @@
|
||||
// Execute `rustlings hint traits1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
trait AppendBar {
|
||||
fn append_bar(self) -> Self;
|
||||
@ -15,6 +14,9 @@ trait AppendBar {
|
||||
|
||||
impl AppendBar for String {
|
||||
// TODO: Implement `AppendBar` for type `String`.
|
||||
fn append_bar(self) -> Self {
|
||||
format!("{}Bar", self)
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {
|
||||
|
||||
@ -8,13 +8,18 @@
|
||||
//
|
||||
// Execute `rustlings hint traits2` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
trait AppendBar {
|
||||
fn append_bar(self) -> Self;
|
||||
}
|
||||
|
||||
// TODO: Implement trait `AppendBar` for a vector of strings.
|
||||
impl AppendBar for Vec<String> {
|
||||
fn append_bar(mut self) -> Self {
|
||||
self.push(String::from("Bar"));
|
||||
self
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
|
||||
@ -8,10 +8,12 @@
|
||||
// Execute `rustlings hint traits3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub trait Licensed {
|
||||
fn licensing_info(&self) -> String;
|
||||
fn licensing_info(&self) -> String{
|
||||
String::from("Some information")
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
struct SomeSoftware {
|
||||
|
||||
@ -7,7 +7,6 @@
|
||||
// Execute `rustlings hint traits4` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub trait Licensed {
|
||||
fn licensing_info(&self) -> String {
|
||||
@ -23,7 +22,7 @@ impl Licensed for SomeSoftware {}
|
||||
impl Licensed for OtherSoftware {}
|
||||
|
||||
// YOU MAY ONLY CHANGE THE NEXT LINE
|
||||
fn compare_license_types(software: ??, software_two: ??) -> bool {
|
||||
fn compare_license_types(software: impl Licensed, software_two: impl Licensed) -> bool {
|
||||
software.licensing_info() == software_two.licensing_info()
|
||||
}
|
||||
|
||||
|
||||
@ -7,7 +7,6 @@
|
||||
// Execute `rustlings hint traits5` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub trait SomeTrait {
|
||||
fn some_function(&self) -> bool {
|
||||
@ -30,7 +29,7 @@ impl SomeTrait for OtherStruct {}
|
||||
impl OtherTrait for OtherStruct {}
|
||||
|
||||
// YOU MAY ONLY CHANGE THE NEXT LINE
|
||||
fn some_func(item: ??) -> bool {
|
||||
fn some_func(item: impl SomeTrait+OtherTrait ) -> bool {
|
||||
item.some_function() && item.other_function()
|
||||
}
|
||||
|
||||
|
||||
@ -8,9 +8,8 @@
|
||||
// Execute `rustlings hint lifetimes1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn longest(x: &str, y: &str) -> &str {
|
||||
fn longest<'a>(x: &'a str, y: &'a str) -> &'a str {
|
||||
if x.len() > y.len() {
|
||||
x
|
||||
} else {
|
||||
|
||||
@ -6,7 +6,6 @@
|
||||
// Execute `rustlings hint lifetimes2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn longest<'a>(x: &'a str, y: &'a str) -> &'a str {
|
||||
if x.len() > y.len() {
|
||||
@ -17,11 +16,20 @@ fn longest<'a>(x: &'a str, y: &'a str) -> &'a str {
|
||||
}
|
||||
|
||||
fn main() {
|
||||
// let string1 = String::from("long string is long");
|
||||
// let result;
|
||||
// let string2 = String::from("xyz");
|
||||
// {
|
||||
// result = longest(string1.as_str(), string2.as_str());
|
||||
// }
|
||||
// println!("The longest string is '{}'", result);
|
||||
// OR //
|
||||
// both solves the lifetime issue
|
||||
let string1 = String::from("long string is long");
|
||||
let result;
|
||||
{
|
||||
let string2 = String::from("xyz");
|
||||
result = longest(string1.as_str(), string2.as_str());
|
||||
println!("The longest string is '{}'", result);
|
||||
}
|
||||
println!("The longest string is '{}'", result);
|
||||
}
|
||||
|
||||
@ -5,11 +5,10 @@
|
||||
// Execute `rustlings hint lifetimes3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
struct Book {
|
||||
author: &str,
|
||||
title: &str,
|
||||
struct Book<'a> {
|
||||
author: &'a str,
|
||||
title: &'a str,
|
||||
}
|
||||
|
||||
fn main() {
|
||||
|
||||
@ -10,12 +10,13 @@
|
||||
// Execute `rustlings hint tests1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
#[test]
|
||||
fn you_can_assert() {
|
||||
assert!();
|
||||
// let failed = "This test failed";
|
||||
// assert!(false, "{}" ,failed);
|
||||
assert!(true, "This test failed")
|
||||
}
|
||||
}
|
||||
|
||||
@ -6,12 +6,14 @@
|
||||
// Execute `rustlings hint tests2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
#[test]
|
||||
fn you_can_assert_eq() {
|
||||
assert_eq!();
|
||||
// assert_eq!(2,2);
|
||||
assert_eq!(true, true);
|
||||
assert_eq!(true, true, "This test failed");
|
||||
// assert_eq!(true, false, "This test failed");
|
||||
}
|
||||
}
|
||||
|
||||
@ -7,7 +7,6 @@
|
||||
// Execute `rustlings hint tests3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub fn is_even(num: i32) -> bool {
|
||||
num % 2 == 0
|
||||
@ -19,11 +18,17 @@ mod tests {
|
||||
|
||||
#[test]
|
||||
fn is_true_when_even() {
|
||||
assert!();
|
||||
assert!(is_even(2),"Number is not even");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn is_false_when_odd() {
|
||||
assert!();
|
||||
// assert!(is_even(5),"Number is odd");
|
||||
// remove the above comment to use the test. Commented that because the test fails.
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn expected() {
|
||||
assert_eq!(is_even(5), false,"Expectations Sucks!");
|
||||
}
|
||||
}
|
||||
|
||||
@ -5,7 +5,6 @@
|
||||
// Execute `rustlings hint tests4` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
struct Rectangle {
|
||||
width: i32,
|
||||
@ -27,20 +26,25 @@ mod tests {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
|
||||
fn correct_width_and_height() {
|
||||
// This test should check if the rectangle is the size that we pass into its constructor
|
||||
let rect = Rectangle::new(10, 20);
|
||||
assert_eq!(???, 10); // check width
|
||||
assert_eq!(???, 20); // check height
|
||||
assert_eq!(rect.width, 10); // check width
|
||||
assert_eq!(rect.height, 20); // check height
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[should_panic(expected = "Rectangle width and height cannot be negative!")]
|
||||
// This test should check if program panics when we try to create rectangle with negative width
|
||||
// and height. #[should_panic] attribute is used to check if the panic message is as expected
|
||||
fn negative_width() {
|
||||
// This test should check if program panics when we try to create rectangle with negative width
|
||||
let _rect = Rectangle::new(-10, 10);
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[should_panic(expected = "Rectangle width and height cannot be negative!")]
|
||||
fn negative_height() {
|
||||
// This test should check if program panics when we try to create rectangle with negative height
|
||||
let _rect = Rectangle::new(10, -10);
|
||||
|
||||
@ -9,18 +9,17 @@
|
||||
// Execute `rustlings hint iterators1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[test]
|
||||
fn main() {
|
||||
let my_fav_fruits = vec!["banana", "custard apple", "avocado", "peach", "raspberry"];
|
||||
|
||||
let mut my_iterable_fav_fruits = ???; // TODO: Step 1
|
||||
let mut my_iterable_fav_fruits = my_fav_fruits.iter(); // TODO: Step 1
|
||||
|
||||
assert_eq!(my_iterable_fav_fruits.next(), Some(&"banana"));
|
||||
assert_eq!(my_iterable_fav_fruits.next(), ???); // TODO: Step 2
|
||||
assert_eq!(my_iterable_fav_fruits.next(), Some(&"custard apple")); // TODO: Step 2
|
||||
assert_eq!(my_iterable_fav_fruits.next(), Some(&"avocado"));
|
||||
assert_eq!(my_iterable_fav_fruits.next(), ???); // TODO: Step 3
|
||||
assert_eq!(my_iterable_fav_fruits.next(), Some(&"peach")); // TODO: Step 3
|
||||
assert_eq!(my_iterable_fav_fruits.next(), Some(&"raspberry"));
|
||||
assert_eq!(my_iterable_fav_fruits.next(), ???); // TODO: Step 4
|
||||
assert_eq!(my_iterable_fav_fruits.next(), None); // TODO: Step 4
|
||||
}
|
||||
|
||||
@ -6,8 +6,6 @@
|
||||
// Execute `rustlings hint iterators2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
// Step 1.
|
||||
// Complete the `capitalize_first` function.
|
||||
// "hello" -> "Hello"
|
||||
@ -15,7 +13,7 @@ pub fn capitalize_first(input: &str) -> String {
|
||||
let mut c = input.chars();
|
||||
match c.next() {
|
||||
None => String::new(),
|
||||
Some(first) => ???,
|
||||
Some(first) => first.to_uppercase().collect::<String>() + c.as_str(),
|
||||
}
|
||||
}
|
||||
|
||||
@ -24,7 +22,11 @@ pub fn capitalize_first(input: &str) -> String {
|
||||
// Return a vector of strings.
|
||||
// ["hello", "world"] -> ["Hello", "World"]
|
||||
pub fn capitalize_words_vector(words: &[&str]) -> Vec<String> {
|
||||
vec![]
|
||||
let mut vec = vec![];
|
||||
for word in words {
|
||||
vec.push(capitalize_first(word));
|
||||
}
|
||||
vec
|
||||
}
|
||||
|
||||
// Step 3.
|
||||
@ -32,7 +34,13 @@ pub fn capitalize_words_vector(words: &[&str]) -> Vec<String> {
|
||||
// Return a single string.
|
||||
// ["hello", " ", "world"] -> "Hello World"
|
||||
pub fn capitalize_words_string(words: &[&str]) -> String {
|
||||
String::new()
|
||||
let mut vec: Vec<String> = vec![];
|
||||
for word in words {
|
||||
vec.push(capitalize_first(word));
|
||||
}
|
||||
vec.join("")
|
||||
// let words :impl Iterator<Item = String> = words.iter().map(|word| capitalize_first(word));
|
||||
// words.collect::<String>()
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
||||
@ -9,7 +9,6 @@
|
||||
// Execute `rustlings hint iterators3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[derive(Debug, PartialEq, Eq)]
|
||||
pub enum DivisionError {
|
||||
@ -26,23 +25,52 @@ pub struct NotDivisibleError {
|
||||
// Calculate `a` divided by `b` if `a` is evenly divisible by `b`.
|
||||
// Otherwise, return a suitable error.
|
||||
pub fn divide(a: i32, b: i32) -> Result<i32, DivisionError> {
|
||||
todo!();
|
||||
if b ==0{
|
||||
return Err(DivisionError::DivideByZero);
|
||||
}
|
||||
else if b!=0 && a%b!=0{
|
||||
return Err(DivisionError::NotDivisible(NotDivisibleError{dividend: a, divisor: b}));
|
||||
}
|
||||
else {
|
||||
return Ok(a/b);
|
||||
}
|
||||
}
|
||||
|
||||
// Complete the function and return a value of the correct type so the test
|
||||
// passes.
|
||||
// Desired output: Ok([1, 11, 1426, 3])
|
||||
fn result_with_list() -> () {
|
||||
fn result_with_list() -> Result<Vec<i32>,DivisionError> {
|
||||
let numbers = vec![27, 297, 38502, 81];
|
||||
let division_results = numbers.into_iter().map(|n| divide(n, 27));
|
||||
Ok(division_results.collect::<Result<Vec<i32>,DivisionError>>()?)
|
||||
// let mut vec = vec![];
|
||||
// for result in division_results {
|
||||
// match result {
|
||||
// Ok(n) => vec.push(n),
|
||||
// Err(e) => return Err(e),
|
||||
// }
|
||||
// }
|
||||
// Ok(vec)
|
||||
|
||||
}
|
||||
|
||||
// Complete the function and return a value of the correct type so the test
|
||||
// passes.
|
||||
// Desired output: [Ok(1), Ok(11), Ok(1426), Ok(3)]
|
||||
fn list_of_results() -> () {
|
||||
fn list_of_results() -> Vec<Result<i32, DivisionError>>{
|
||||
let numbers = vec![27, 297, 38502, 81];
|
||||
let division_results = numbers.into_iter().map(|n| divide(n, 27));
|
||||
division_results.collect()
|
||||
// OR
|
||||
|
||||
// division_results.collect::<Vec<Result<i32, DivisionError>>>()?
|
||||
|
||||
// OR
|
||||
|
||||
// let mut vec = vec![];
|
||||
// for n in numbers {
|
||||
// vec.push(divide(n, 27));
|
||||
// }
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
||||
@ -3,7 +3,6 @@
|
||||
// Execute `rustlings hint iterators4` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub fn factorial(num: u64) -> u64 {
|
||||
// Complete this function to return the factorial of num
|
||||
@ -15,6 +14,10 @@ pub fn factorial(num: u64) -> u64 {
|
||||
// For an extra challenge, don't use:
|
||||
// - recursion
|
||||
// Execute `rustlings hint iterators4` for hints.
|
||||
(1..=num).fold(1, |f,n| f*n)
|
||||
// fold better than normal for loop. it uses an functional programming approach
|
||||
|
||||
// (1..=num).product()
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
||||
@ -11,7 +11,6 @@
|
||||
// Execute `rustlings hint iterators5` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::collections::HashMap;
|
||||
|
||||
@ -33,9 +32,9 @@ fn count_for(map: &HashMap<String, Progress>, value: Progress) -> usize {
|
||||
}
|
||||
|
||||
fn count_iterator(map: &HashMap<String, Progress>, value: Progress) -> usize {
|
||||
// map is a hashmap with String keys and Progress values.
|
||||
// map = { "variables1": Complete, "from_str": None, ... }
|
||||
todo!();
|
||||
// map.values().filter(|&val| *val == value).count()
|
||||
map.iter().filter(|(_, &val)| val == value).count()
|
||||
// map.iter().fold(0, |acc, (_, &val)| if val == value { acc + 1 } else { acc })
|
||||
}
|
||||
|
||||
fn count_collection_for(collection: &[HashMap<String, Progress>], value: Progress) -> usize {
|
||||
@ -54,7 +53,12 @@ fn count_collection_iterator(collection: &[HashMap<String, Progress>], value: Pr
|
||||
// collection is a slice of hashmaps.
|
||||
// collection = [{ "variables1": Complete, "from_str": None, ... },
|
||||
// { "variables2": Complete, ... }, ... ]
|
||||
todo!();
|
||||
// collection
|
||||
// .iter()
|
||||
// .map(|map| count_iterator(map, value))
|
||||
// .sum()
|
||||
collection.iter().fold(0,|acc, map|acc+ count_iterator(map, value))
|
||||
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
||||
@ -21,19 +21,41 @@
|
||||
//
|
||||
// Execute `rustlings hint arc1` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#![forbid(unused_imports)] // Do not change this, (or the next) line.
|
||||
use std::sync::Arc;
|
||||
use std::thread;
|
||||
|
||||
fn main() {
|
||||
let numbers: Vec<_> = (0..100u32).collect();
|
||||
let shared_numbers = // TODO
|
||||
|
||||
let shared_numbers = Arc::new(numbers); // TODO
|
||||
let mut joinhandles = Vec::new();
|
||||
|
||||
//The difference between Box and Arc is that Box is for single-threaded and Arc is for multi-threaded
|
||||
// what Arc new does is it takes the ownership of the data and then it creates a reference to the data and then it gives the ownership of the reference to the other threads.
|
||||
// what Arc::clone does is it increases the reference count of the data and then it gives the ownership of the reference to the other threads.
|
||||
|
||||
// what happens when i use Rc instead of Arc in below code , explain with examples
|
||||
//Rc is not thread safe, so if we use Rc instead of Arc, the code will not compile.
|
||||
//Rc is used for single-threaded reference counting, while Arc is used for multi-threaded reference counting.
|
||||
// can you explain the working of below code with Rc and Arc and compare?
|
||||
//The code creates a Vec of u32 called "numbers" with values ranging from 0 to 99. It then creates an Arc of the Vec, which is used to share the data across multiple threads. It then creates 8 threads, each of which sums every eighth value with an offset. The threads use the Arc to access the data, and then print the sum of the values for each offset.
|
||||
//If we use Rc instead of Arc, the code will not compile, because Rc is not thread safe. Rc is used for single-threaded reference counting, while Arc is used for multi-threaded reference counting.
|
||||
|
||||
// is Arc provides mutable reference or immutable reference to threads?
|
||||
//Arc provides immutable reference to threads. It allows multiple threads to have read-only access to the data, but it does not allow any thread to have write access to the data. if we want to have mutable access to the data, we can use Mutex or RwLock in combination with Arc.
|
||||
// can we have mutable referrence usign Rc?
|
||||
//No, Rc only provides immutable reference to the data. If we want to have mutable access to the data, we can use RefCell in combination with Rc.
|
||||
//How use RefCell with Rc?
|
||||
//RefCell is a type that provides interior mutability, which means that it allows us to mutate the data even when it is behind an immutable reference. We can use RefCell in combination with Rc by wrapping the data in a RefCell, and then using Rc to share the data across multiple threads.
|
||||
// can you explain how to use RefCell with Rc and then using Rc to share the data across multiple threads?
|
||||
//To use RefCell with Rc, we first wrap the data in a RefCell, and then use Rc to share the data across multiple threads. We can then use the borrow and borrow_mut methods of RefCell to get immutable and mutable references to the data, respectively. This allows us to mutate the data even when it is behind an immutable reference, which is useful when sharing the data across multiple threads.
|
||||
// can you explain how to use Mutex with Arc and then using Arc to share the data across multiple threads with code example?
|
||||
//To use Mutex with Arc, we first wrap the data in a Mutex, and then use Arc to share the data across multiple threads. We can then use the lock method of Mutex to get a mutable reference to the data, which allows us to mutate the data safely across multiple threads. This is useful when we need to have mutable access to the data, but want to ensure that the mutations are synchronized and safe across multiple threads.
|
||||
// can you explain how to use RwLock with Arc and then using Arc to share the data across multiple threads with code example?
|
||||
//To use RwLock with Arc, we first wrap the data in a RwLock, and then use Arc to share the data across multiple threads. We can then use the read and write methods of RwLock to get immutable and mutable references to the data, respectively. This allows us to have multiple threads with read-only access to the data, or one thread with write access to the data, while ensuring that the access is synchronized and safe across multiple threads.
|
||||
for offset in 0..8 {
|
||||
let child_numbers = // TODO
|
||||
let child_numbers = Arc::clone(&shared_numbers); // TODO
|
||||
joinhandles.push(thread::spawn(move || {
|
||||
let sum: u32 = child_numbers.iter().filter(|&&n| n % 8 == offset).sum();
|
||||
println!("Sum of offset {} is {}", offset, sum);
|
||||
@ -42,4 +64,48 @@ fn main() {
|
||||
for handle in joinhandles.into_iter() {
|
||||
handle.join().unwrap();
|
||||
}
|
||||
//output of above code:
|
||||
|
||||
// Output:
|
||||
// ====================
|
||||
// Sum of offset 0 is 624
|
||||
// Sum of offset 4 is 576
|
||||
// Sum of offset 5 is 588
|
||||
// Sum of offset 6 is 600
|
||||
// Sum of offset 2 is 650
|
||||
// Sum of offset 1 is 637
|
||||
// Sum of offset 3 is 663
|
||||
// Sum of offset 7 is 612
|
||||
|
||||
// ====================
|
||||
|
||||
// find the difference between the above and below code's output
|
||||
// for offset in 0..8 {
|
||||
// let child_numbers = Arc::clone(&shared_numbers); // TODO
|
||||
// joinhandles.push(thread::spawn(move || {
|
||||
// let sum: u32 = child_numbers.iter().filter(|&&n| n % 8 == offset).sum();
|
||||
// println!("Sum of offset {} is {}", offset, sum);
|
||||
// }).join());
|
||||
//waiting for the threads to finish after they are spawned, then only going to create another thread.
|
||||
// }
|
||||
// for handle in joinhandles.into_iter() {
|
||||
// handle.unwrap();
|
||||
// }
|
||||
|
||||
// output of commented code:
|
||||
|
||||
// Output:
|
||||
// ====================
|
||||
// Sum of offset 0 is 624
|
||||
// Sum of offset 1 is 637
|
||||
// Sum of offset 2 is 650
|
||||
// Sum of offset 3 is 663
|
||||
// Sum of offset 4 is 576
|
||||
// Sum of offset 5 is 588
|
||||
// Sum of offset 6 is 600
|
||||
// Sum of offset 7 is 612
|
||||
|
||||
// ====================
|
||||
|
||||
|
||||
}
|
||||
|
||||
@ -18,11 +18,10 @@
|
||||
//
|
||||
// Execute `rustlings hint box1` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
#[derive(PartialEq, Debug)]
|
||||
pub enum List {
|
||||
Cons(i32, List),
|
||||
Cons(i32, Box<List>),
|
||||
Nil,
|
||||
}
|
||||
|
||||
@ -35,11 +34,13 @@ fn main() {
|
||||
}
|
||||
|
||||
pub fn create_empty_list() -> List {
|
||||
todo!()
|
||||
List::Nil
|
||||
}
|
||||
|
||||
pub fn create_non_empty_list() -> List {
|
||||
todo!()
|
||||
List::Cons(23, Box::new(List::Cons(55, Box::new(List::Nil))))
|
||||
|
||||
//cons_list is more kind of a linked list
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
||||
@ -12,7 +12,6 @@
|
||||
//
|
||||
// Execute `rustlings hint cow1` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::borrow::Cow;
|
||||
|
||||
@ -48,7 +47,8 @@ mod tests {
|
||||
let slice = [0, 1, 2];
|
||||
let mut input = Cow::from(&slice[..]);
|
||||
match abs_all(&mut input) {
|
||||
// TODO
|
||||
Cow::Borrowed(_) => Ok(()),
|
||||
_ => Err("Expected borrowed value"),
|
||||
}
|
||||
}
|
||||
|
||||
@ -60,7 +60,8 @@ mod tests {
|
||||
let slice = vec![0, 1, 2];
|
||||
let mut input = Cow::from(slice);
|
||||
match abs_all(&mut input) {
|
||||
// TODO
|
||||
Cow::Owned(_) => Ok(()),
|
||||
_ => Err("Expected owned value"),
|
||||
}
|
||||
}
|
||||
|
||||
@ -72,7 +73,8 @@ mod tests {
|
||||
let slice = vec![-1, 0, 1];
|
||||
let mut input = Cow::from(slice);
|
||||
match abs_all(&mut input) {
|
||||
// TODO
|
||||
Cow::Owned(_) => Ok(()),
|
||||
_ => Err("Expected owned value"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -10,7 +10,6 @@
|
||||
//
|
||||
// Execute `rustlings hint rc1` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::rc::Rc;
|
||||
|
||||
@ -34,6 +33,21 @@ impl Planet {
|
||||
println!("Hi from {:?}!", self)
|
||||
}
|
||||
}
|
||||
//what is the difference between Strong and Weak count?
|
||||
//Strong count is the number of Rc pointers to the data, and Weak count is the number of Weak pointers to the data.
|
||||
//Rc::strong_count(&sun) returns the number of strong (Rc) pointers to the data, and Rc::weak_count(&sun) returns the number of weak (Weak) pointers to the data.
|
||||
// what is Rc pointers and Weak pointers?
|
||||
//Rc pointers are reference counted pointers, which means that they keep track of the number of references to the data they point to, and automatically deallocate the data when the number of references drops to zero.
|
||||
//Weak pointers are similar to Rc pointers, but they do not keep the data alive. They are used to break reference cycles, where two or more objects reference each other, and thus keep each other alive, even though they are no longer needed.
|
||||
//Rc pointers are used to keep the data alive, while Weak pointers are used to break reference cycles.
|
||||
// what is reference cycles?
|
||||
//Reference cycles occur when two or more objects reference each other, and thus keep each other alive, even though they are no longer needed. This can lead to memory leaks, where memory is not deallocated even though it is no longer needed.\
|
||||
//give example of reference cycles?
|
||||
//An example of a reference cycle is a parent and a child object that reference each other. If the parent object has a reference to the child object, and the child object has a reference to the parent object, then they will keep each other alive, even though they are no longer needed.
|
||||
// how to find out weak count using Rc?
|
||||
//Rc::weak_count(&sun) returns the number of weak (Weak) pointers to the data.
|
||||
// what is the use of Rc::clone()?
|
||||
//Rc::clone() is used to create a new reference to the same data. It increases the reference count, so that the data is not deallocated until all references are dropped.
|
||||
|
||||
#[test]
|
||||
fn main() {
|
||||
@ -61,17 +75,17 @@ fn main() {
|
||||
jupiter.details();
|
||||
|
||||
// TODO
|
||||
let saturn = Planet::Saturn(Rc::new(Sun {}));
|
||||
let saturn = Planet::Saturn(Rc::clone(&sun));
|
||||
println!("reference count = {}", Rc::strong_count(&sun)); // 7 references
|
||||
saturn.details();
|
||||
|
||||
// TODO
|
||||
let uranus = Planet::Uranus(Rc::new(Sun {}));
|
||||
let uranus = Planet::Uranus(Rc::clone(&sun));
|
||||
println!("reference count = {}", Rc::strong_count(&sun)); // 8 references
|
||||
uranus.details();
|
||||
|
||||
// TODO
|
||||
let neptune = Planet::Neptune(Rc::new(Sun {}));
|
||||
let neptune = Planet::Neptune(Rc::clone(&sun));
|
||||
println!("reference count = {}", Rc::strong_count(&sun)); // 9 references
|
||||
neptune.details();
|
||||
|
||||
@ -93,12 +107,15 @@ fn main() {
|
||||
println!("reference count = {}", Rc::strong_count(&sun)); // 4 references
|
||||
|
||||
// TODO
|
||||
drop(earth);
|
||||
println!("reference count = {}", Rc::strong_count(&sun)); // 3 references
|
||||
|
||||
// TODO
|
||||
drop(venus);
|
||||
println!("reference count = {}", Rc::strong_count(&sun)); // 2 references
|
||||
|
||||
// TODO
|
||||
drop(mercury);
|
||||
println!("reference count = {}", Rc::strong_count(&sun)); // 1 reference
|
||||
|
||||
assert_eq!(Rc::strong_count(&sun), 1);
|
||||
|
||||
@ -8,7 +8,6 @@
|
||||
// Execute `rustlings hint threads1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::thread;
|
||||
use std::time::{Duration, Instant};
|
||||
@ -26,7 +25,7 @@ fn main() {
|
||||
|
||||
let mut results: Vec<u128> = vec![];
|
||||
for handle in handles {
|
||||
// TODO: a struct is returned from thread::spawn, can you use it?
|
||||
results.push(handle.join().unwrap());
|
||||
}
|
||||
|
||||
if results.len() != 10 {
|
||||
|
||||
@ -7,9 +7,8 @@
|
||||
// Execute `rustlings hint threads2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::sync::Arc;
|
||||
use std::sync::{Arc,Mutex};
|
||||
use std::thread;
|
||||
use std::time::Duration;
|
||||
|
||||
@ -18,13 +17,14 @@ struct JobStatus {
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let status = Arc::new(JobStatus { jobs_completed: 0 });
|
||||
let status = Arc::new(Mutex::new(JobStatus { jobs_completed: 0 }));
|
||||
let mut handles = vec![];
|
||||
for _ in 0..10 {
|
||||
let status_shared = Arc::clone(&status);
|
||||
let handle = thread::spawn(move || {
|
||||
thread::sleep(Duration::from_millis(250));
|
||||
// TODO: You must take an action before you update a shared value
|
||||
let mut status_shared = status_shared.lock().unwrap();
|
||||
status_shared.jobs_completed += 1;
|
||||
});
|
||||
handles.push(handle);
|
||||
@ -34,6 +34,6 @@ fn main() {
|
||||
// TODO: Print the value of the JobStatus.jobs_completed. Did you notice
|
||||
// anything interesting in the output? Do you have to 'join' on all the
|
||||
// handles?
|
||||
println!("jobs completed {}", ???);
|
||||
println!("jobs completed {}", status.lock().unwrap().jobs_completed);
|
||||
}
|
||||
}
|
||||
|
||||
@ -3,7 +3,6 @@
|
||||
// Execute `rustlings hint threads3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
use std::sync::mpsc;
|
||||
use std::sync::Arc;
|
||||
@ -30,11 +29,11 @@ fn send_tx(q: Queue, tx: mpsc::Sender<u32>) -> () {
|
||||
let qc = Arc::new(q);
|
||||
let qc1 = Arc::clone(&qc);
|
||||
let qc2 = Arc::clone(&qc);
|
||||
|
||||
let tx1 = tx.clone();
|
||||
thread::spawn(move || {
|
||||
for val in &qc1.first_half {
|
||||
println!("sending {:?}", val);
|
||||
tx.send(*val).unwrap();
|
||||
tx1.send(*val).unwrap();
|
||||
thread::sleep(Duration::from_secs(1));
|
||||
}
|
||||
});
|
||||
@ -46,6 +45,15 @@ fn send_tx(q: Queue, tx: mpsc::Sender<u32>) -> () {
|
||||
thread::sleep(Duration::from_secs(1));
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
//In the given code, you have used the Arc (Atomic Reference Counting) to share ownership of the Queue struct between multiple threads. This allows you to have multiple producers by cloning the Arc reference.
|
||||
|
||||
// By using Arc::clone(&qc), you create a new reference to the Arc that can be moved into a new thread. This ensures that each thread has its own reference to the shared Queue struct.
|
||||
|
||||
// In this case, you have two threads, each with its own cloned reference to the Queue struct. Each thread then iterates over a different half of the queue and sends the values through the mpsc::Sender.
|
||||
|
||||
// This way, you achieve multiple producers by sharing ownership of the Queue struct using Arc and cloning the reference for each thread.
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
||||
@ -3,7 +3,6 @@
|
||||
// Execute `rustlings hint macros1` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
macro_rules! my_macro {
|
||||
() => {
|
||||
@ -12,5 +11,5 @@ macro_rules! my_macro {
|
||||
}
|
||||
|
||||
fn main() {
|
||||
my_macro();
|
||||
my_macro!();
|
||||
}
|
||||
|
||||
@ -3,14 +3,14 @@
|
||||
// Execute `rustlings hint macros2` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
fn main() {
|
||||
my_macro!();
|
||||
}
|
||||
|
||||
macro_rules! my_macro {
|
||||
() => {
|
||||
println!("Check out my macro!");
|
||||
};
|
||||
}
|
||||
|
||||
fn main() {
|
||||
my_macro!();
|
||||
}
|
||||
|
||||
@ -5,9 +5,9 @@
|
||||
// Execute `rustlings hint macros3` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
mod macros {
|
||||
#[macro_export]
|
||||
macro_rules! my_macro {
|
||||
() => {
|
||||
println!("Check out my macro!");
|
||||
|
||||
@ -3,16 +3,29 @@
|
||||
// Execute `rustlings hint macros4` or use the `hint` watch subcommand for a
|
||||
// hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
//learn more about macros here: https://veykril.github.io/tlborm/
|
||||
|
||||
|
||||
|
||||
// #[rustfmt::skip]
|
||||
/// This is a custom macro called `my_macro`.
|
||||
///
|
||||
/// It can be used to print messages to the console.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// ```
|
||||
/// my_macro!(); // Prints: "Check out my macro!"
|
||||
/// my_macro!("Hello, world!"); // Prints: "Look at this other macro: Hello, world!"
|
||||
/// ```
|
||||
#[rustfmt::skip]
|
||||
macro_rules! my_macro {
|
||||
() => {
|
||||
println!("Check out my macro!");
|
||||
}
|
||||
};
|
||||
($val:expr) => {
|
||||
println!("Look at this other macro: {}", $val);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
fn main() {
|
||||
|
||||
@ -14,10 +14,10 @@
|
||||
use std::f32;
|
||||
|
||||
fn main() {
|
||||
let pi = 3.14f32;
|
||||
// let pi = consts::PI;
|
||||
let radius = 5.00f32;
|
||||
|
||||
let area = pi * f32::powi(radius, 2);
|
||||
let area = f32::consts::PI * f32::powi(radius, 2);
|
||||
|
||||
println!(
|
||||
"The area of a circle with radius {:.2} is {:.5}!",
|
||||
|
||||
@ -13,10 +13,18 @@
|
||||
//
|
||||
// No hints this time ;)
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
// Put your function here!
|
||||
// fn calculate_price_of_apples {
|
||||
fn calculate_price_of_apples(quantity: i32) -> i32{
|
||||
let mut price = 0;
|
||||
if quantity > 40 {
|
||||
price = quantity;
|
||||
} else {
|
||||
price = quantity * 2;
|
||||
}
|
||||
price
|
||||
}
|
||||
|
||||
// Don't modify this function!
|
||||
#[test]
|
||||
|
||||
@ -20,7 +20,6 @@
|
||||
//
|
||||
// No hints this time!
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub enum Command {
|
||||
Uppercase,
|
||||
@ -32,11 +31,16 @@ mod my_module {
|
||||
use super::Command;
|
||||
|
||||
// TODO: Complete the function signature!
|
||||
pub fn transformer(input: ???) -> ??? {
|
||||
pub fn transformer(input: Vec<(String, Command)>) -> Vec<String> {
|
||||
// TODO: Complete the output declaration!
|
||||
let mut output: ??? = vec![];
|
||||
let mut output: Vec<String> = vec![];
|
||||
for (string, command) in input.iter() {
|
||||
// TODO: Complete the function body. You can do it!
|
||||
match command {
|
||||
Command::Uppercase => output.push(string.to_uppercase()),
|
||||
Command::Trim => output.push(string.trim().to_string()),
|
||||
Command::Append(n) => output.push(string.to_string() + (&"bar".repeat(*n))),
|
||||
}
|
||||
}
|
||||
output
|
||||
}
|
||||
@ -45,7 +49,7 @@ mod my_module {
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
// TODO: What do we need to import to have `transformer` in scope?
|
||||
use ???;
|
||||
use crate::my_module::transformer;
|
||||
use super::Command;
|
||||
|
||||
#[test]
|
||||
|
||||
@ -16,15 +16,14 @@
|
||||
//
|
||||
// Execute `rustlings hint quiz3` or use the `hint` watch subcommand for a hint.
|
||||
|
||||
// I AM NOT DONE
|
||||
|
||||
pub struct ReportCard {
|
||||
pub grade: f32,
|
||||
pub struct ReportCard<T> {
|
||||
pub grade: T,
|
||||
pub student_name: String,
|
||||
pub student_age: u8,
|
||||
}
|
||||
|
||||
impl ReportCard {
|
||||
impl <T: std::fmt::Display> ReportCard <T> {
|
||||
pub fn print(&self) -> String {
|
||||
format!("{} ({}) - achieved a grade of {}",
|
||||
&self.student_name, &self.student_age, &self.grade)
|
||||
@ -52,7 +51,7 @@ mod tests {
|
||||
fn generate_alphabetic_report_card() {
|
||||
// TODO: Make sure to change the grade here after you finish the exercise.
|
||||
let report_card = ReportCard {
|
||||
grade: 2.1,
|
||||
grade: "A+",
|
||||
student_name: "Gary Plotter".to_string(),
|
||||
student_age: 11,
|
||||
};
|
||||
|
||||
1
rustlings
Submodule
1
rustlings
Submodule
@ -0,0 +1 @@
|
||||
Subproject commit 9a743f80c57cc6bf27819589a8ddb5a5579ab1a4
|
||||
@ -12,7 +12,7 @@ const RUSTC_EDITION_ARGS: &[&str] = &["--edition", "2021"];
|
||||
const RUSTC_NO_DEBUG_ARGS: &[&str] = &["-C", "strip=debuginfo"];
|
||||
const I_AM_DONE_REGEX: &str = r"(?m)^\s*///?\s*I\s+AM\s+NOT\s+DONE";
|
||||
const CONTEXT: usize = 2;
|
||||
const CLIPPY_CARGO_TOML_PATH: &str = "./exercises/22_clippy/Cargo.toml";
|
||||
const CLIPPY_CARGO_TOML_PATH: &str = "./exercises/clippy/Cargo.toml";
|
||||
|
||||
// Get a temporary file name that is hopefully unique
|
||||
#[inline]
|
||||
@ -375,4 +375,4 @@ mod test {
|
||||
let out = exercise.compile().unwrap().run().unwrap();
|
||||
assert!(out.stdout.contains("THIS TEST TOO SHALL PASS"));
|
||||
}
|
||||
}
|
||||
}
|
||||
Loading…
x
Reference in New Issue
Block a user