Merge pull request #219 from Tanish-Eagle/editting-compound-types
Editting compound types
This commit is contained in:
commit
b5d490bbb4
|
@ -1,26 +1,26 @@
|
|||
# Array
|
||||
The type of array is `[T; Lengh]`, as you can see, array's lengh is part of their type signature. So their length must be known at compile time.
|
||||
The type of array is `[T; Length]`, as you can see, array's length is part of their type signature. So their length must be known at compile time.
|
||||
|
||||
For example, you cant initialized an array as below:
|
||||
For example, you cant initialize an array like below:
|
||||
```rust
|
||||
fn init_arr(n: i32) {
|
||||
let arr = [1; n];
|
||||
}
|
||||
```
|
||||
|
||||
This will cause an error, because the compile have no idea of the exact size of the array in compile time.
|
||||
This will cause an error, because the compiler has no idea of the exact size of the array at compile time.
|
||||
|
||||
1. 🌟
|
||||
```rust,editable
|
||||
|
||||
fn main() {
|
||||
// fill the blank with proper array type
|
||||
// Fill the blank with proper array type
|
||||
let arr: __ = [1, 2, 3, 4, 5];
|
||||
|
||||
// modify below to make it work
|
||||
// Modify the code below to make it work
|
||||
assert!(arr.len() == 4);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -28,16 +28,16 @@ fn main() {
|
|||
```rust,editable
|
||||
|
||||
fn main() {
|
||||
// we can ignore parts of the array type or even the whole type, let the compiler infer it for us
|
||||
// We can ignore parts of the array type or even the whole type, let the compiler infer it for us
|
||||
let arr0 = [1, 2, 3];
|
||||
let arr: [_; 3] = ['a', 'b', 'c'];
|
||||
|
||||
// fill the blank
|
||||
// Arrays are stack allocated, `std::mem::size_of_val` return the bytes which array occupies
|
||||
// A char takes 4 byte in Rust: Unicode char
|
||||
// Fill the blank
|
||||
// Arrays are stack allocated, `std::mem::size_of_val` returns the bytes which an array occupies
|
||||
// A char takes 4 bytes in Rust: Unicode char
|
||||
assert!(std::mem::size_of_val(&arr) == __);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -46,13 +46,13 @@ fn main() {
|
|||
```rust,editable
|
||||
|
||||
fn main() {
|
||||
// fill the blank
|
||||
// Fill the blank
|
||||
let list: [i32; 100] = __ ;
|
||||
|
||||
assert!(list[0] == 1);
|
||||
assert!(list.len() == 100);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -60,10 +60,10 @@ fn main() {
|
|||
```rust,editable
|
||||
|
||||
fn main() {
|
||||
// fix the error
|
||||
// Fix the error
|
||||
let _arr = [1, 2, '3'];
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -73,28 +73,28 @@ fn main() {
|
|||
fn main() {
|
||||
let arr = ['a', 'b', 'c'];
|
||||
|
||||
let ele = arr[1]; // only modify this line to make the code work!
|
||||
let ele = arr[1]; // Only modify this line to make the code work!
|
||||
|
||||
assert!(ele == 'a');
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
6. 🌟 Out of bounds indexing causes `panic`.
|
||||
```rust,editable
|
||||
|
||||
// fix the error
|
||||
// Fix the error
|
||||
fn main() {
|
||||
let names = [String::from("Sunfei"), "Sunface".to_string()];
|
||||
|
||||
// `get` returns an Option<T>, it's safe to use
|
||||
// `Get` returns an Option<T>, it's safe to use
|
||||
let name0 = names.get(0).unwrap();
|
||||
|
||||
// but indexing is not safe
|
||||
// But indexing is not safe
|
||||
let _name1 = &names[2];
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
|
||||
```
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
|
||||
```rust,editable
|
||||
|
||||
// fix the errors
|
||||
// Fix the errors
|
||||
enum Number {
|
||||
Zero,
|
||||
One,
|
||||
|
@ -25,18 +25,18 @@ enum Number2 {
|
|||
|
||||
|
||||
fn main() {
|
||||
// a enum variant can be converted to a integer by `as`
|
||||
// An enum variant can be converted to a integer by `as`
|
||||
assert_eq!(Number::One, Number1::One);
|
||||
assert_eq!(Number1::One, Number2::One);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
2. 🌟 each enum variant can hold its own data.
|
||||
2. 🌟 Each enum variant can hold its own data.
|
||||
```rust,editable
|
||||
|
||||
// fill in the blank
|
||||
// Fill in the blank
|
||||
enum Message {
|
||||
Quit,
|
||||
Move { x: i32, y: i32 },
|
||||
|
@ -45,17 +45,17 @@ enum Message {
|
|||
}
|
||||
|
||||
fn main() {
|
||||
let msg1 = Message::Move{__}; // instantiating with x = 1, y = 2
|
||||
let msg2 = Message::Write(__); // instantiating with "hello, world!"
|
||||
let msg1 = Message::Move{__}; // Instantiating with x = 1, y = 2
|
||||
let msg2 = Message::Write(__); // Instantiating with "hello, world!"
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
3. 🌟🌟 we can get the data which a enum variant is holding by pattern match
|
||||
3. 🌟🌟 We can get the data which an enum variant is holding by pattern match.
|
||||
```rust,editable
|
||||
|
||||
// fill in the blank and fix the error
|
||||
// Fill in the blank and fix the error
|
||||
enum Message {
|
||||
Quit,
|
||||
Move { x: i32, y: i32 },
|
||||
|
@ -72,7 +72,7 @@ fn main() {
|
|||
panic!("NEVER LET THIS RUN!");
|
||||
}
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -80,7 +80,7 @@ fn main() {
|
|||
|
||||
```rust,editable
|
||||
|
||||
// fill in the blank and fix the errors
|
||||
// Fill in the blank and fix the errors
|
||||
enum Message {
|
||||
Quit,
|
||||
Move { x: i32, y: i32 },
|
||||
|
@ -105,11 +105,11 @@ fn show_message(msg: Message) {
|
|||
}
|
||||
```
|
||||
|
||||
5. 🌟🌟 As there is no `null` in Rust, we have to use enum `Option<T>` to deal the cases when value is absent.
|
||||
5. 🌟🌟 Since there is no `null` in Rust, we have to use enum `Option<T>` to deal with the cases when the value is absent.
|
||||
```rust,editable
|
||||
|
||||
// fill in the blank to make the `println` work.
|
||||
// also add some code to prevent the `panic` from running.
|
||||
// Fill in the blank to make the `println` work.
|
||||
// Also add some code to prevent the `panic` from running.
|
||||
fn main() {
|
||||
let five = Some(5);
|
||||
let six = plus_one(five);
|
||||
|
@ -118,7 +118,7 @@ fn main() {
|
|||
if let __ = six {
|
||||
println!("{}", n);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
|
||||
panic!("NEVER LET THIS RUN!");
|
||||
|
@ -133,7 +133,7 @@ fn plus_one(x: Option<i32>) -> Option<i32> {
|
|||
```
|
||||
|
||||
|
||||
6. 🌟🌟🌟🌟 implement a `linked-list` via enums.
|
||||
6. 🌟🌟🌟🌟 Implement a `linked-list` via enums.
|
||||
|
||||
```rust,editable
|
||||
|
||||
|
@ -166,12 +166,12 @@ impl List {
|
|||
// depends on the variant of `self`
|
||||
// `self` has type `&List`, and `*self` has type `List`, matching on a
|
||||
// concrete type `T` is preferred over a match on a reference `&T`
|
||||
// after Rust 2018 you can use self here and tail (with no ref) below as well,
|
||||
// After Rust 2018 you can use self here and tail (with no ref) below as well,
|
||||
// rust will infer &s and ref tail.
|
||||
// See https://doc.rust-lang.org/edition-guide/rust-2018/ownership-and-lifetimes/default-match-bindings.html
|
||||
match *self {
|
||||
// Can't take ownership of the tail, because `self` is borrowed;
|
||||
// instead take a reference to the tail
|
||||
// Instead take a reference to the tail
|
||||
Cons(_, ref tail) => 1 + tail.len(),
|
||||
// Base Case: An empty list has zero length
|
||||
Nil => 0
|
||||
|
|
|
@ -4,18 +4,18 @@ Slices are similar to arrays, but their length is not known at compile time, so
|
|||
1. 🌟🌟 Here, both `[i32]` and `str` are slice types, but directly using it will cause errors. You have to use the reference of the slice instead: `&[i32]`, `&str`.
|
||||
```rust,editable
|
||||
|
||||
// fix the errors, DON'T add new lines!
|
||||
// Fix the errors, DON'T add new lines!
|
||||
fn main() {
|
||||
let arr = [1, 2, 3];
|
||||
let s1: [i32] = arr[0..2];
|
||||
|
||||
let s2: str = "hello, world" as str;
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
A slice reference is a two-word object, for simplicity reasons, from now on we will use slice instead of `slice reference`. The first word is a pointer to the data, and the second word is the length of the slice. The word size is the same as usize, determined by the processor architecture eg 64 bits on an x86-64. Slices can be used to borrow a section of an array, and have the type signature `&[T]`.
|
||||
A slice reference is a two-word object, for simplicity reasons, from now on we will use slice instead of `slice reference`. The first word is a pointer to the data, and the second word is the length of the slice. The word size is the same as usize, determined by the processor architecture, eg 64 bits on an x86-64. Slices can be used to borrow a section of an array, and have the type signature `&[T]`.
|
||||
|
||||
2. 🌟🌟🌟
|
||||
```rust,editable
|
||||
|
@ -25,11 +25,11 @@ fn main() {
|
|||
|
||||
let slice = &arr[..2];
|
||||
|
||||
// modify '6' to make it work
|
||||
// TIPS: slice( reference ) IS NOT an array, if it is an array, then `assert!` will passed: each of the two UTF-8 chars '中' and '国' occupies 3 bytes, 2 * 3 = 6
|
||||
// Modify '6' to make it work
|
||||
// TIPS: slice( reference ) IS NOT an array, if it is an array, then `assert!` will passed: Each of the two UTF-8 chars '中' and '国' occupies 3 bytes, 2 * 3 = 6
|
||||
assert!(std::mem::size_of_val(&slice) == 6);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -38,15 +38,15 @@ fn main() {
|
|||
|
||||
fn main() {
|
||||
let arr: [i32; 5] = [1, 2, 3, 4, 5];
|
||||
// fill the blanks to make the code work
|
||||
// Fill the blanks to make the code work
|
||||
let slice: __ = __;
|
||||
assert_eq!(slice, &[2, 3, 4]);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
### string slices
|
||||
### String slices
|
||||
4. 🌟
|
||||
```rust,editable
|
||||
|
||||
|
@ -54,12 +54,12 @@ fn main() {
|
|||
let s = String::from("hello");
|
||||
|
||||
let slice1 = &s[0..2];
|
||||
// fill the blank to make the code work, DON'T USE 0..2 again
|
||||
// Fill the blank to make the code work, DON'T USE 0..2 again
|
||||
let slice2 = &s[__];
|
||||
|
||||
assert_eq!(slice1, slice2);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -68,24 +68,24 @@ fn main() {
|
|||
|
||||
fn main() {
|
||||
let s = "你好,世界";
|
||||
// modify this line to make the code work
|
||||
// Modify this line to make the code work
|
||||
let slice = &s[0..2];
|
||||
|
||||
assert!(slice == "你");
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
6. 🌟🌟 `&String` can be implicitly converted into `&str`.
|
||||
```rust,editable
|
||||
|
||||
// fix errors
|
||||
// Fix errors
|
||||
fn main() {
|
||||
let mut s = String::from("hello world");
|
||||
|
||||
// here, &s is `&String` type, but `first_word` need a `&str` type.
|
||||
// it works because `&String` can be implicitly converted to `&str, If you want know more ,this is called `Deref`
|
||||
// Here, &s is `&String` type, but `first_word` need a `&str` type.
|
||||
// It works because `&String` can be implicitly converted to `&str, If you want know more ,this is called `Deref`
|
||||
let word = first_word(&s);
|
||||
|
||||
s.clear(); // error!
|
||||
|
|
|
@ -1,17 +1,17 @@
|
|||
# string
|
||||
# String
|
||||
The type of string literal `"hello, world"` is `&str`, e.g `let s: &str = "hello, world"`.
|
||||
|
||||
|
||||
### str and &str
|
||||
1. 🌟 We can't use `str` type in normal ways, but we can use `&str`
|
||||
### Str and &str
|
||||
1. 🌟 We can't use `str` type in normal ways, but we can use `&str`.
|
||||
|
||||
```rust,editable
|
||||
|
||||
// fix error without adding new line
|
||||
// Fix error without adding new line
|
||||
fn main() {
|
||||
let s: str = "hello, world";
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -20,7 +20,7 @@ fn main() {
|
|||
|
||||
```rust,editable
|
||||
|
||||
// fix the error with at least two solutions
|
||||
// Fix the error with at least two solutions
|
||||
fn main() {
|
||||
let s: Box<str> = "hello, world".into();
|
||||
greetings(s)
|
||||
|
@ -37,7 +37,7 @@ fn greetings(s: &str) {
|
|||
3. 🌟
|
||||
```rust,editable
|
||||
|
||||
// fill the blank
|
||||
// Fill the blank
|
||||
fn main() {
|
||||
let mut s = __;
|
||||
s.push_str("hello, world");
|
||||
|
@ -45,28 +45,28 @@ fn main() {
|
|||
|
||||
assert_eq!(s, "hello, world!");
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
4. 🌟🌟🌟
|
||||
```rust,editable
|
||||
|
||||
// fix all errors without adding newline
|
||||
// Fix all errors without adding newline
|
||||
fn main() {
|
||||
let s = String::from("hello");
|
||||
s.push(',');
|
||||
s.push(" world");
|
||||
s += "!".to_string();
|
||||
|
||||
println!("{}", s)
|
||||
println!("{}", s);
|
||||
}
|
||||
```
|
||||
|
||||
5. 🌟🌟 `replace` can be used to replace substring
|
||||
```rust,editable
|
||||
|
||||
// fill the blank
|
||||
// Fill the blank
|
||||
fn main() {
|
||||
let s = String::from("I like dogs");
|
||||
// Allocate new memory and store the modified string there
|
||||
|
@ -74,17 +74,17 @@ fn main() {
|
|||
|
||||
assert_eq!(s1, "I like cats");
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
More `String` methods can be found under [String](https://doc.rust-lang.org/std/string/struct.String.html) module.
|
||||
|
||||
6. 🌟🌟 You can only concat a `String` with `&str`, and `String`'s ownership can be moved to another variable
|
||||
6. 🌟🌟 You can only concat a `String` with `&str`, and `String`'s ownership can be moved to another variable.
|
||||
|
||||
```rust,editable
|
||||
|
||||
// fix errors without removing any line
|
||||
// Fix errors without removing any line
|
||||
fn main() {
|
||||
let s1 = String::from("hello,");
|
||||
let s2 = String::from("world!");
|
||||
|
@ -100,7 +100,7 @@ Opsite to the seldom using of `str`, `&str` and `String` are used everywhere!
|
|||
7. 🌟🌟 `&str` can be converted to `String` in two ways
|
||||
```rust,editable
|
||||
|
||||
// fix error with at lest two solutions
|
||||
// Fix error with at least two solutions
|
||||
fn main() {
|
||||
let s = "hello, world";
|
||||
greetings(s)
|
||||
|
@ -115,25 +115,25 @@ fn greetings(s: String) {
|
|||
|
||||
```rust,editable
|
||||
|
||||
// use two approaches to fix the error and without adding a new line
|
||||
// Use two approaches to fix the error and without adding a new line
|
||||
fn main() {
|
||||
let s = "hello, world".to_string();
|
||||
let s1: &str = s;
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
### string escapes
|
||||
### String escapes
|
||||
9. 🌟
|
||||
```rust,editable
|
||||
fn main() {
|
||||
// You can use escapes to write bytes by their hexadecimal values
|
||||
// fill the blank below to show "I'm writing Rust"
|
||||
// Fill the blank below to show "I'm writing Rust"
|
||||
let byte_escape = "I'm writing Ru\x73__!";
|
||||
println!("What are you doing\x3F (\\x3F means ?) {}", byte_escape);
|
||||
|
||||
// ...or Unicode code points.
|
||||
// ...Or Unicode code points.
|
||||
let unicode_codepoint = "\u{211D}";
|
||||
let character_name = "\"DOUBLE-STRUCK CAPITAL R\"";
|
||||
|
||||
|
@ -169,11 +169,11 @@ fn main() {
|
|||
let long_delimiter = __;
|
||||
assert_eq!(long_delimiter, "Hello, \"##\"");
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
### byte string
|
||||
### Byte string
|
||||
Want a string that's not UTF-8? (Remember, str and String must be valid UTF-8). Or maybe you want an array of bytes that's mostly text? Byte strings to the rescue!
|
||||
|
||||
**Example**:
|
||||
|
@ -189,8 +189,8 @@ fn main() {
|
|||
|
||||
// Byte strings can have byte escapes...
|
||||
let escaped = b"\x52\x75\x73\x74 as bytes";
|
||||
// ...but no unicode escapes
|
||||
// let escaped = b"\u{211D} is not allowed";
|
||||
// ...But no unicode escapes
|
||||
// let escaped = b"\u{211D} Is not allowed";
|
||||
println!("Some escaped bytes: {:?}", escaped);
|
||||
|
||||
|
||||
|
@ -207,7 +207,7 @@ fn main() {
|
|||
like with normal raw strings"#;
|
||||
|
||||
// Byte strings don't have to be UTF-8
|
||||
let shift_jis = b"\x82\xe6\x82\xa8\x82\xb1\x82\xbb"; // "ようこそ" in SHIFT-JIS
|
||||
let shift_jis = b"\x82\xe6\x82\xa8\x82\xb1\x82\xbb"; // "ようこそ" In SHIFT-JIS
|
||||
|
||||
// But then they can't always be converted to `str`
|
||||
match str::from_utf8(shift_jis) {
|
||||
|
@ -219,29 +219,29 @@ fn main() {
|
|||
|
||||
A more detailed listing of the ways to write string literals and escape characters is given in the ['Tokens' chapter](https://doc.rust-lang.org/reference/tokens.html) of the Rust Reference.
|
||||
|
||||
### string index
|
||||
### String index
|
||||
11. 🌟🌟🌟 You can't use index to access a char in a string, but you can use slice `&s1[start..end]`.
|
||||
|
||||
```rust,editable
|
||||
|
||||
fn main() {
|
||||
let s1 = String::from("hi,中国");
|
||||
let h = s1[0]; //modify this line to fix the error, tips: `h` only takes 1 byte in UTF8 format
|
||||
let h = s1[0]; // Modify this line to fix the error, tips: `h` only takes 1 byte in UTF8 format
|
||||
assert_eq!(h, "h");
|
||||
|
||||
let h1 = &s1[3..5];//modify this line to fix the error, tips: `中` takes 3 bytes in UTF8 format
|
||||
let h1 = &s1[3..5]; // Modify this line to fix the error, tips: `中` takes 3 bytes in UTF8 format
|
||||
assert_eq!(h1, "中");
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
### operate on UTF8 string
|
||||
### Operate on UTF8 string
|
||||
12. 🌟
|
||||
```rust,editable
|
||||
|
||||
fn main() {
|
||||
// fill the blank to print each char in "你好,世界"
|
||||
// Fill the blank to print each char in "你好,世界"
|
||||
for c in "你好,世界".__ {
|
||||
println!("{}", c)
|
||||
}
|
||||
|
|
|
@ -1,10 +1,10 @@
|
|||
# Struct
|
||||
|
||||
### There types of structs
|
||||
### The types of structs
|
||||
1. 🌟 We must specify concrete values for each of the fields in struct.
|
||||
```rust,editable
|
||||
|
||||
// fix the error
|
||||
// Fix the error
|
||||
struct Person {
|
||||
name: String,
|
||||
age: u8,
|
||||
|
@ -17,7 +17,7 @@ fn main() {
|
|||
age,
|
||||
};
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -27,35 +27,35 @@ fn main() {
|
|||
|
||||
struct Unit;
|
||||
trait SomeTrait {
|
||||
// ...Some behavours defines here
|
||||
// ...Some behaviors defined here.
|
||||
}
|
||||
|
||||
// We don't care the the fields are in Unit, but we care its behaviors.
|
||||
// We don't care about what fields are in the Unit, but we care about its behaviors.
|
||||
// So we use a struct with no fields and implement some behaviors for it
|
||||
impl SomeTrait for Unit { }
|
||||
fn main() {
|
||||
let u = Unit;
|
||||
do_something_with_unit(u);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
|
||||
// fill the blank to make the code work
|
||||
// Fill the blank to make the code work
|
||||
fn do_something_with_unit(u: __) { }
|
||||
```
|
||||
|
||||
3. 🌟🌟🌟 Tuple struct looks similar to tuples, it has added meaning the struct name provides but has no named fields. It's useful when you want give the whole tuple a name, but don't care the fields's names.
|
||||
3. 🌟🌟🌟 Tuple struct looks similar to tuples, it has added meaning the struct name provides but has no named fields. It's useful when you want to give the whole tuple a name, but don't care about the fields's names.
|
||||
|
||||
```rust,editable
|
||||
|
||||
// fix the error and fill the blanks
|
||||
// Fix the error and fill the blanks
|
||||
struct Color(i32, i32, i32);
|
||||
struct Point(i32, i32, i32);
|
||||
fn main() {
|
||||
let v = Point(__, __, __);
|
||||
check_color(v);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
|
||||
fn check_color(p: Color) {
|
||||
|
@ -66,13 +66,13 @@ fn check_color(p: Color) {
|
|||
}
|
||||
```
|
||||
|
||||
### Operate on structs
|
||||
### Operating on structs
|
||||
|
||||
4. 🌟 You can make a whole struct mutable when instantiate it, but Rust doesn't allow us to mark only certain fields as mutable.
|
||||
4. 🌟 You can make a whole struct mutable when instantiating it, but Rust doesn't allow us to mark only certain fields as mutable.
|
||||
|
||||
```rust,editable
|
||||
|
||||
// fill the blank and fix the error without adding/removing new line
|
||||
// Fill the blank and fix the error without adding/removing new line
|
||||
struct Person {
|
||||
name: String,
|
||||
age: u8,
|
||||
|
@ -84,26 +84,26 @@ fn main() {
|
|||
age,
|
||||
};
|
||||
|
||||
// how can you believe sunface is only 18?
|
||||
// How can you believe sunface is only 18?
|
||||
p.age = 30;
|
||||
|
||||
// fill the lank
|
||||
// Fill the blank
|
||||
__ = String::from("sunfei");
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
5. 🌟 Using *field init shorthand syntax* to reduct repetitions.
|
||||
5. 🌟 Using *field init shorthand syntax* to reduce repetitions.
|
||||
```rust,editable
|
||||
|
||||
// fill the blank
|
||||
// Fill the blank
|
||||
struct Person {
|
||||
name: String,
|
||||
age: u8,
|
||||
}
|
||||
fn main() {
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
|
||||
fn build_person(name: String, age: u8) -> Person {
|
||||
|
@ -117,7 +117,7 @@ fn build_person(name: String, age: u8) -> Person {
|
|||
6. 🌟 You can create instance from other instance with *struct update syntax*
|
||||
```rust,editable
|
||||
|
||||
// fill the blank to make the code work
|
||||
// Fill the blank to make the code work
|
||||
struct User {
|
||||
active: bool,
|
||||
username: String,
|
||||
|
@ -134,7 +134,7 @@ fn main() {
|
|||
|
||||
let u2 = set_email(u1);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
|
||||
fn set_email(u: User) -> User {
|
||||
|
@ -146,11 +146,11 @@ fn set_email(u: User) -> User {
|
|||
```
|
||||
|
||||
### Print the structs
|
||||
7. 🌟🌟 We can use `#[derive(Debug)]` to [make a struct prinable](https://doc.rust-lang.org/book/ch05-02-example-structs.html?highlight=%23%5Bderive(Debug)%5D#adding-useful-functionality-with-derived-traits).
|
||||
7. 🌟🌟 We can use `#[derive(Debug)]` to [make a struct printable](https://doc.rust-lang.org/book/ch05-02-example-structs.html?highlight=%23%5Bderive(Debug)%5D#adding-useful-functionality-with-derived-traits).
|
||||
|
||||
```rust,editable
|
||||
|
||||
// fill the blanks to make the code work
|
||||
// Fill the blanks to make the code work
|
||||
#[__]
|
||||
struct Rectangle {
|
||||
width: u32,
|
||||
|
@ -160,13 +160,13 @@ struct Rectangle {
|
|||
fn main() {
|
||||
let scale = 2;
|
||||
let rect1 = Rectangle {
|
||||
width: dbg!(30 * scale), // print debug info to stderr and assign the value of `30 * scale` to `width`
|
||||
width: dbg!(30 * scale), // Print debug info to stderr and assign the value of `30 * scale` to `width`
|
||||
height: 50,
|
||||
};
|
||||
|
||||
dbg!(&rect1); // print debug info to stderr
|
||||
dbg!(&rect1); // Print debug info to stderr
|
||||
|
||||
println!(__, rect1); // print debug info to stdout
|
||||
println!(__, rect1); // Print debug info to stdout
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -209,7 +209,7 @@ fn main() {
|
|||
8. 🌟🌟
|
||||
```rust,editable
|
||||
|
||||
// fix errors to make it work
|
||||
// Fix errors to make it work
|
||||
#[derive(Debug)]
|
||||
struct File {
|
||||
name: String,
|
||||
|
|
|
@ -6,29 +6,29 @@ fn main() {
|
|||
let _t0: (u8,i16) = (0, -1);
|
||||
// Tuples can be tuple's members
|
||||
let _t1: (u8, (i16, u32)) = (0, (-1, 1));
|
||||
// fill the blanks to make the code work
|
||||
// Fill the blanks to make the code work
|
||||
let t: (u8, __, i64, __, __) = (1u8, 2u16, 3i64, "hello", String::from(", world"));
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
2. 🌟 Members can be extracted from the tuple using indexing.
|
||||
```rust,editable
|
||||
|
||||
// make it works
|
||||
// Make it work
|
||||
fn main() {
|
||||
let t = ("i", "am", "sunface");
|
||||
assert_eq!(t.1, "sunface");
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
3. 🌟 Long tuples cannot be printed
|
||||
```rust,editable
|
||||
|
||||
// fix the error
|
||||
// Fix the error
|
||||
fn main() {
|
||||
let too_long_tuple = (1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13);
|
||||
println!("too long tuple: {:?}", too_long_tuple);
|
||||
|
@ -41,14 +41,14 @@ fn main() {
|
|||
fn main() {
|
||||
let tup = (1, 6.4, "hello");
|
||||
|
||||
// fill the blank to make the code work
|
||||
// Fill the blank to make the code work
|
||||
let __ = tup;
|
||||
|
||||
assert_eq!(x, 1);
|
||||
assert_eq!(y, "hello");
|
||||
assert_eq!(z, 6.4);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -57,14 +57,14 @@ fn main() {
|
|||
fn main() {
|
||||
let (x, y, z);
|
||||
|
||||
// fill the blank
|
||||
// Fill the blank
|
||||
__ = (1, 2, 3);
|
||||
|
||||
assert_eq!(x, 3);
|
||||
assert_eq!(y, 1);
|
||||
assert_eq!(z, 2);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
```
|
||||
|
||||
|
@ -72,13 +72,13 @@ fn main() {
|
|||
```rust,editable
|
||||
|
||||
fn main() {
|
||||
// fill the blank, need a few computations here.
|
||||
// Fill the blank, need a few computations here.
|
||||
let (x, y) = sum_multiply(__);
|
||||
|
||||
assert_eq!(x, 5);
|
||||
assert_eq!(y, 6);
|
||||
|
||||
println!("Success!")
|
||||
println!("Success!");
|
||||
}
|
||||
|
||||
fn sum_multiply(nums: (i32, i32)) -> (i32, i32) {
|
||||
|
|
Loading…
Reference in New Issue