I write the code according to Chapter 2 "Guessing Game Tutorial".
I then refactored it to use a Custom Type for Validation after reading [https://github.com/rust-lang/book/blob/master/2018-edition/src/ch09-03-to-panic-or-not-to-panic.md](Chapter 9 "To panic! or Not to panic!").
I wrote unit tests to accompany the code.
I've pushed a commit to my Github repo here: https://github.com/ltfschoen/RustTest/blob/251880ced38a9ec42f799d8005a7eddfd5811f2e/projects/guessing_game/src/main.rs.
All the tests pass when I run cargo test
.
And when I compile and run the code with cargo run
outputs the following.
It uses the Custom Type for Validation correctly and displays messages as expected for when I enter a value that is both between the range 0 and 100 and either less than the secret number or greater than the secret number. It panics and displays a message as expected when the user enters a positive value outside the range (i.e. 101 or 0). It exits the program when I enter a guess that matches the secret number as expected.
However, when I enter a negative number (i.e. -1), it triggers an error in the match
operator on Line 67 in my code, which triggers continue
that skips to the next iteration of the loop that just asks for the user to enter another guess, it doesn't reach Line 14 of the Custom Type for Validation.
I'm using Visual Studio Code with breakpoints but I still do not understand why.
The secret number is: 83
Input your guess.
82
You guessed: Guess { value: 82 }
Too small!
Input your guess.
84
You guessed: Guess { value: 84 }
Too big!
Input your guess.
83
You guessed: Guess { value: 83 }
You win!
Ls /Users/Ls/code/clones/RustTest/projects/guessing_game [git:master]
$ cargo run
Finished dev [unoptimized + debuginfo] target(s) in 0.0 secs
Running `target/debug/guessing_game`
The secret number is: 54
Input your guess.
100
You guessed: Guess { value: 100 }
Too big!
Input your guess.
101
thread 'main' panicked at 'Guess value must be between 1 and 100, got 101.', src/main.rs:16:13
note: Run with `RUST_BACKTRACE=1` for a backtrace.
Ls /Users/Ls/code/clones/RustTest/projects/guessing_game [git:master]
$ cargo run
Finished dev [unoptimized + debuginfo] target(s) in 0.0 secs
Running `target/debug/guessing_game`
The secret number is: 48
Input your guess.
-1
Input your guess.
I tried to replicate the scenario at https://play.rust-lang.org/ with the following code, but it matches the arm Ok
instead of Err
and outputs Success: -1
, which differs from what's happening in my Github repo Rust script.
let mut guess: String = "-1".to_string();
let guess: String = match guess.trim().parse() {
Ok(num) => { println!("Success: {}", num); num }, // Success: -1
Err(err) => { println!("Error: {}", err); err.to_string() },
};
Note: If you want to run my script after cloning my repo, run the following:
cd projects/guessing_game;
cargo run;
cargo test;
Initially I didn't understand why entering a negative value for the user input guess of -1 wasn't able to triggered the Ok
match arm and ran the Custom Type Validator where it would panic, and instead ran Err
arm and restarted the loop of asking for a guess from the user....
But after writing this post I made some changes and got it to work successfully with the Custom Type for Validations and panic for negative input values, which I've published in this commit
$ cargo run
Compiling guessing_game v0.1.0 (file:///Users/Ls/code/clones/RustTest/projects/guessing_game)
Finished dev [unoptimized + debuginfo] target(s) in 0.65 secs
Running `target/debug/guessing_game`
The secret number is: 31
Input your guess.
-1
thread 'main' panicked at 'Guess value must be between 1 and 100, got -1.', src/main.rs:16:13
note: Run with `RUST_BACKTRACE=1` for a backtrace.
But why can't I change secret_number
to be a u32
instead of i32
?
i.e. on Line 26 why doesn't it work when I change it to
pub fn comparison(&self, secret_number: &u32) -> i32 {
and on Line 100 why doesn't it work when I change it to:
let actual_secret_number: u32 = 50;
It gives error message: expected i32, found u32