Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Clean up Chapter 1 (Hello World) #1650

Merged
merged 1 commit into from
Dec 8, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 7 additions & 7 deletions src/hello.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,19 @@
This is the source code of the traditional Hello World program.

```rust,editable
// This is a comment, and is ignored by the compiler
// This is a comment, and is ignored by the compiler.
// You can test this code by clicking the "Run" button over there ->
// or if you prefer to use your keyboard, you can use the "Ctrl + Enter" shortcut
// or if you prefer to use your keyboard, you can use the "Ctrl + Enter"
// shortcut.

// This code is editable, feel free to hack it!
// You can always return to the original code by clicking the "Reset" button ->

// This is the main function
// This is the main function.
fn main() {
// Statements here are executed when the compiled binary is called
// Statements here are executed when the compiled binary is called.

// Print text to the console
// Print text to the console.
println!("Hello World!");
}
```
Expand All @@ -38,8 +39,7 @@ Hello World!
### Activity

Click 'Run' above to see the expected output. Next, add a new
line with a second `println!` macro so that the output
shows:
line with a second `println!` macro so that the output shows:

```text
Hello World!
Expand Down
30 changes: 14 additions & 16 deletions src/hello/comment.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,30 +4,29 @@ Any program requires comments, and Rust supports
a few different varieties:

* *Regular comments* which are ignored by the compiler:
* `// Line comments which go to the end of the line.`
* `/* Block comments which go to the closing delimiter. */`
* *Doc comments* which are parsed into HTML library
[documentation][docs]:
* `/// Generate library docs for the following item.`
* `//! Generate library docs for the enclosing item.`
* `// Line comments which go to the end of the line.`
* `/* Block comments which go to the closing delimiter. */`
* *Doc comments* which are parsed into HTML library [documentation][docs]:
* `/// Generate library docs for the following item.`
* `//! Generate library docs for the enclosing item.`

```rust,editable
fn main() {
// This is an example of a line comment
// There are two slashes at the beginning of the line
// And nothing written inside these will be read by the compiler
// This is an example of a line comment.
// There are two slashes at the beginning of the line.
// And nothing written inside these will be read by the compiler.

// println!("Hello, world!");

// Run it. See? Now try deleting the two slashes, and run it again.

/*
/*
* This is another type of comment, a block comment. In general,
* line comments are the recommended comment style. But
* block comments are extremely useful for temporarily disabling
* chunks of code. /* Block comments can be /* nested, */ */
* so it takes only a few keystrokes to comment out everything
* in this main() function. /*/*/* Try it yourself! */*/*/
* line comments are the recommended comment style. But block comments
* are extremely useful for temporarily disabling chunks of code.
* /* Block comments can be /* nested, */ */ so it takes only a few
* keystrokes to comment out everything in this main() function.
* /*/*/* Try it yourself! */*/*/
*/

/*
Expand All @@ -41,7 +40,6 @@ fn main() {
let x = 5 + /* 90 + */ 5;
println!("Is `x` 10 or 100? x = {}", x);
}

```

### See also:
Expand Down
55 changes: 28 additions & 27 deletions src/hello/print.md
Original file line number Diff line number Diff line change
@@ -1,12 +1,14 @@
# Formatted print

Printing is handled by a series of [`macros`][macros] defined in [`std::fmt`][fmt]
some of which include:
Printing is handled by a series of [`macros`][macros] defined in
[`std::fmt`][fmt] some of which include:

* `format!`: write formatted text to [`String`][string]
* `print!`: same as `format!` but the text is printed to the console (io::stdout).
* `print!`: same as `format!` but the text is printed to the console
(io::stdout).
* `println!`: same as `print!` but a newline is appended.
* `eprint!`: same as `print!` but the text is printed to the standard error (io::stderr).
* `eprint!`: same as `print!` but the text is printed to the standard error
(io::stderr).
* `eprintln!`: same as `eprint!` but a newline is appended.

All parse text in the same fashion. As a plus, Rust checks formatting
Expand All @@ -20,7 +22,7 @@ fn main() {

// Positional arguments can be used. Specifying an integer inside `{}`
// determines which additional argument will be replaced. Arguments start
// at 0 immediately after the format string
// at 0 immediately after the format string.
println!("{0}, this is {1}. {1}, this is {0}", "Alice", "Bob");

// As can named arguments.
Expand All @@ -29,13 +31,13 @@ fn main() {
subject="the quick brown fox",
verb="jumps over");

// Different formatting can be invoked by specifying the format character after a
// `:`.
println!("Base 10: {}", 69420); //69420
println!("Base 2 (binary): {:b}", 69420); //10000111100101100
println!("Base 8 (octal): {:o}", 69420); //207454
println!("Base 16 (hexadecimal): {:x}", 69420); //10f2c
println!("Base 16 (hexadecimal): {:X}", 69420); //10F2C
// Different formatting can be invoked by specifying the format character
// after a `:`.
println!("Base 10: {}", 69420); // 69420
println!("Base 2 (binary): {:b}", 69420); // 10000111100101100
println!("Base 8 (octal): {:o}", 69420); // 207454
println!("Base 16 (hexadecimal): {:x}", 69420); // 10f2c
println!("Base 16 (hexadecimal): {:X}", 69420); // 10F2C


// You can right-justify text with a specified width. This will
Expand All @@ -46,29 +48,28 @@ fn main() {
//and left-adjust by flipping the sign. This will output "10000".
println!("{number:0<5}", number=1);

// You can use named arguments in the format specifier by appending a `$`
// You can use named arguments in the format specifier by appending a `$`.
println!("{number:0>width$}", number=1, width=5);


// Rust even checks to make sure the correct number of arguments are
// used.
// Rust even checks to make sure the correct number of arguments are used.
println!("My name is {0}, {1} {0}", "Bond");
// FIXME ^ Add the missing argument: "James"

// Only types that implement fmt::Display can be formatted with `{}`. User-
// defined types do not implement fmt::Display by default
// defined types do not implement fmt::Display by default.

#[allow(dead_code)]
struct Structure(i32);

// This will not compile because `Structure` does not implement
// fmt::Display
// fmt::Display.
//println!("This struct `{}` won't print...", Structure(3));
// TODO ^ Try uncommenting this line

// For Rust 1.58 and above, you can directly capture the argument from a
// surrounding variable. Just like the above, this will output
// " 1". 4 white spaces and a "1".
// " 1", 4 white spaces and a "1".
let number: f64 = 1.0;
let width: usize = 5;
println!("{number:>width$}");
Expand All @@ -80,7 +81,7 @@ of text. The base form of two important ones are listed below:

* `fmt::Debug`: Uses the `{:?}` marker. Format text for debugging purposes.
* `fmt::Display`: Uses the `{}` marker. Format text in a more elegant, user
friendly fashion.
friendly fashion.

Here, we used `fmt::Display` because the std library provides implementations
for these types. To print text for custom types, more steps are required.
Expand All @@ -90,14 +91,14 @@ Implementing the `fmt::Display` trait automatically implements the

### Activities

* Fix the issue in the above code (see FIXME) so that it runs without
error.
* Try uncommenting the line that attempts to format the `Structure` struct (see TODO)
* Add a `println!` macro call that prints: `Pi is roughly 3.142` by controlling
the number of decimal places shown. For the purposes of this exercise,
use `let pi = 3.141592` as an estimate for pi. (Hint: you may need to
check the [`std::fmt`][fmt] documentation for setting the number of
decimals to display)
* Fix the issue in the above code (see FIXME) so that it runs without
error.
* Try uncommenting the line that attempts to format the `Structure` struct
(see TODO)
* Add a `println!` macro call that prints: `Pi is roughly 3.142` by controlling
the number of decimal places shown. For the purposes of this exercise, use
`let pi = 3.141592` as an estimate for pi. (Hint: you may need to check the
[`std::fmt`][fmt] documentation for setting the number of decimals to display)

### See also:

Expand Down
13 changes: 7 additions & 6 deletions src/hello/print/fmt.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,7 @@
We've seen that formatting is specified via a *format string*:

* `format!("{}", foo)` -> `"3735928559"`
* `format!("0x{:X}", foo)` ->
[`"0xDEADBEEF"`][deadbeef]
* `format!("0x{:X}", foo)` -> [`"0xDEADBEEF"`][deadbeef]
* `format!("0o{:o}", foo)` -> `"0o33653337357"`

The same variable (`foo`) can be formatted differently depending on which
Expand All @@ -26,13 +25,13 @@ struct City {
}

impl Display for City {
// `f` is a buffer, and this method must write the formatted string into it
// `f` is a buffer, and this method must write the formatted string into it.
fn fmt(&self, f: &mut Formatter) -> fmt::Result {
let lat_c = if self.lat >= 0.0 { 'N' } else { 'S' };
let lon_c = if self.lon >= 0.0 { 'E' } else { 'W' };

// `write!` is like `format!`, but it will write the formatted string
// into a buffer (the first argument)
// into a buffer (the first argument).
write!(f, "{}: {:.3}°{} {:.3}°{}",
self.name, self.lat.abs(), lat_c, self.lon.abs(), lon_c)
}
Expand Down Expand Up @@ -69,6 +68,7 @@ You can view a [full list of formatting traits][fmt_traits] and their argument
types in the [`std::fmt`][fmt] documentation.

### Activity

Add an implementation of the `fmt::Display` trait for the `Color` struct above
so that the output displays as:

Expand All @@ -79,8 +79,9 @@ RGB (0, 0, 0) 0x000000
```

Two hints if you get stuck:
* You [may need to list each color more than once][named_parameters],
* You can [pad with zeros to a width of 2][fmt_width] with `:0>2`.

* You [may need to list each color more than once][named_parameters].
* You can [pad with zeros to a width of 2][fmt_width] with `:0>2`.

### See also:

Expand Down
6 changes: 3 additions & 3 deletions src/hello/print/print_debug.md
Original file line number Diff line number Diff line change
Expand Up @@ -43,15 +43,15 @@ fn main() {

// `Structure` is printable!
println!("Now {:?} will print!", Structure(3));

// The problem with `derive` is there is no control over how
// the results look. What if I want this to just show a `7`?
println!("Now {:?} will print!", Deep(Structure(7)));
}
```

So `fmt::Debug` definitely makes this printable but sacrifices some
elegance. Rust also provides "pretty printing" with `{:#?}`.
So `fmt::Debug` definitely makes this printable but sacrifices some elegance.
Rust also provides "pretty printing" with `{:#?}`.

```rust,editable
#[derive(Debug)]
Expand Down
11 changes: 5 additions & 6 deletions src/hello/print/print_display.md
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ or for any other generic containers. `fmt::Debug` must then be used for these
generic cases.

This is not a problem though because for any new *container* type which is
*not* generic,`fmt::Display` can be implemented.
*not* generic, `fmt::Display` can be implemented.

```rust,editable
use std::fmt; // Import `fmt`
Expand All @@ -66,7 +66,7 @@ struct Point2D {
y: f64,
}

// Similarly, implement `Display` for `Point2D`
// Similarly, implement `Display` for `Point2D`.
impl fmt::Display for Point2D {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
// Customize so only `x` and `y` are denoted.
Expand Down Expand Up @@ -100,10 +100,9 @@ fn main() {
}
```

So, `fmt::Display` has been implemented but `fmt::Binary` has not, and
therefore cannot be used. `std::fmt` has many such [`traits`][traits] and
each requires its own implementation. This is detailed further in
[`std::fmt`][fmt].
So, `fmt::Display` has been implemented but `fmt::Binary` has not, and therefore
cannot be used. `std::fmt` has many such [`traits`][traits] and each requires
its own implementation. This is detailed further in [`std::fmt`][fmt].

### Activity

Expand Down
3 changes: 2 additions & 1 deletion src/hello/print/print_display/testcase_list.md
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,8 @@ fn main() {

### Activity

Try changing the program so that the index of each element in the vector is also printed. The new output should look like this:
Try changing the program so that the index of each element in the vector is also
printed. The new output should look like this:

```rust,ignore
[0: 1, 1: 2, 2: 3]
Expand Down