{"id":20452345,"url":"https://github.com/zakharb/rustguide","last_synced_at":"2026-04-04T06:12:28.333Z","repository":{"id":142500008,"uuid":"603994807","full_name":"zakharb/RustGuide","owner":"zakharb","description":"Rust docs","archived":false,"fork":false,"pushed_at":"2023-03-03T22:59:41.000Z","size":1216,"stargazers_count":4,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-04-06T19:11:15.206Z","etag":null,"topics":["cheatsheet","learning","rust","rust-examples","rust-learning"],"latest_commit_sha":null,"homepage":"","language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/zakharb.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-02-20T05:25:40.000Z","updated_at":"2024-08-22T02:44:13.000Z","dependencies_parsed_at":null,"dependency_job_id":"769304b0-14d8-47c4-a8f8-7046815a6ade","html_url":"https://github.com/zakharb/RustGuide","commit_stats":null,"previous_names":["zakharb/rustguide"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/zakharb/RustGuide","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zakharb%2FRustGuide","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zakharb%2FRustGuide/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zakharb%2FRustGuide/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zakharb%2FRustGuide/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/zakharb","download_url":"https://codeload.github.com/zakharb/RustGuide/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zakharb%2FRustGuide/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":276801522,"owners_count":25707312,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-09-24T02:00:09.776Z","response_time":97,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["cheatsheet","learning","rust","rust-examples","rust-learning"],"created_at":"2024-11-15T11:09:04.710Z","updated_at":"2025-09-24T18:31:04.966Z","avatar_url":"https://github.com/zakharb.png","language":"Rust","readme":"# Content  \n- [1 Getting Started](#1-getting-started)  \n- [2 Programming a Guessing Game](#2-programming-a-guessing-game)  \n- [3 Comming Programming Concepts](#3-comming-programming-concepts)  \n- [4 Ownership](#4-ownership)  \n- [5 Using Structs](#5-using-structs)  \n- [6 Enums and Pattern Matching](#6-enums-and-pattern-matching)  \n- [7 Packages Crates and Modules](#7-packages-crates-and-modules)  \n- [8 Common Collections](#8-common-collections)  \n- [9 Error Handling](#9-error-handling)  \n- [10 Generic Types Traits Lifetimes](#10-generic-types-traits-lifetimes)  \n- [11 How to Write Tests](#11-how-to-write-tests)  \n- [12 Building a Command Line Program](#12-building-a-command-line-program)  \n- [13 Functional Language Features](#13-functional-fanguage-features)  \n- [14 More About Cargo](#14-more-about-cargo)  \n- [15 Smart Pointers](#15-smart-pointers)  \n\n# 1 Getting Started\n\n## Installation\nInstall\n```sh\ncurl --proto '=https' --tlsv1.3 https://sh.rustup.rs -sSf | sh\n```\n\nCheck, update, uninstall\n```sh\nrustc --version\nrustup update\nrustup self uninstall\n```\n\n## Hello, World!\nIt’s traditional when learning a new language to write a little program that prints the text `Hello, world!` to the screen, so we’ll do the same here!\n\n### Creating a Project Directory\nWe suggest making a `projects directory` in your home directory and keeping all your projects there\n```sh\nmkdir ~/projects\ncd ~/projects\nmkdir hello_world\ncd hello_world\n```\n\n### Writing and Running a Rust Program\nNext, make a new source file and call it main.rs. \n```rust\nfn main() {\n    println!(\"Hello, world!\");\n}\n```\n\nCompile\n```sh\nrustc main.rs\n./main\n```\n\n### Anatomy of a Rust Program\nThese lines define a function named `main`. The function body is wrapped in `{}`\n```rust\nfn main() {\n\n}\n```\n\n\u003e If you want to stick to a standard style across Rust projects, you can use an automatic formatter tool called `rustfmt`\n\n- Rust style is to indent with `four spaces`, not a tab\n- println! calls a `Rust macro`\n- we pass string as an argument to `println!`\n- we end the line with a semicolon `(;)`\n\n### Compiling and Running Are Separate Steps\nBefore running a Rust program, you must compile it using `rustc`\n```sh\nrustc main.rs\n```\n## Hello, Cargo!\n`Cargo` is Rust’s build system and `package manager`. \n\n### Creating a Project with Cargo\nLet’s create a new project using Cargo\n```sh\ncargo new hello_cargo\ncd hello_cargo\n```\n\nFilename: Cargo.toml - Cargo’s configuration file.\n```tm\n[package]\nname = \"hello_cargo\"\nversion = \"0.1.0\"\nedition = \"2021\"\n\n# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html\n\n[dependencies]\n```\n\n### Building and Running a Cargo Project\nBuild project \n```sh\ncargo build\n```\nBecause the default build is a debug build, Cargo puts the binary in a directory named debug. You can run the executable with this command:\n```sh\n./target/debug/hello_cargo\n```\n\nWe can also use cargo run to compile the code and then `run` the resultant executable `all in one` command:\n```sh\ncargo run\n```\n\nThis command quickly `checks` your code to make sure it compiles but doesn’t produce an executable\n```sh\ncargo check\n```\n\n### Building for Release\nWhen your project is finally ready for release, you can use command to compile it with optimizations.\n```sh\ncargo --build release\n```\n\n# 2 Programming a Guessing Game\nWe’ll implement a classic beginner programming problem: a guessing game. Here’s how it works: the program will generate a random integer between 1 and 100. It will then prompt the player to enter a guess. After a guess is entered, the program will indicate whether the guess is too low or too high. If the guess is correct, the game will print a congratulatory message and exit.\n\n## Setting Up a New Project\nGo to the projects directory and make a `new project` using `Cargo`\n```sh\ncargo new guessing_game\ncd guessing_game\n```\n\n## Processing a Guess\nThe first part of the guessing game program will ask for user input, process that input, and check that the input is in the expected form.\n```rust\nuse std::io; //standard library, known as std\n\nfn main() { //the entry point\n    println!(\"Guess the number!\"); //macro that prints a string to the screen\n    println!(\"Please input your guess.\"); // macro println!\n    let mut guess = String::new();\n    io::stdin()\n        .read_line(\u0026mut guess)\n        .expect(\"Failed to read line\");\n    println!(\"You guessed: {guess}\");\n}\n```\n\n### Storing Values with Variables\nNext, we’ll create a variable to store the user input, like this:\n```rust\n    let mut guess = String::new();\n```\n\nTo make a variable mutable, we add mut before the variable name:\n```rust\nlet apples = 5; // immutable\nlet mut bananas = 5; // mutable\n```\n\nIn full, the let mut guess = String::new(); line has created a mutable variable that is currently bound to a new, empty instance of a String:  \n- `let mut guess` will introduce a `mutable variable` named `guess`  \n- equal sign `(=)` tells Rust we want to `bind` something to the variable  \n- `::` syntax in the `::new` line indicates that new is an associated function of the `String` type  \n\n### Receiving User Input\nCall the `stdin` function from the `io` module, which will allow us to handle user `input`:\n```rust\n    io::stdin()\n        .read_line(\u0026mut guess)\n```\n\u003e If we hadn’t `imported` the io library with `use std::io`; at the beginning of the program, we could still use the function by writing this function call as `std::io::stdin`.\n\nNext, the line `.read_line(\u0026mut guess)` calls the `read_line` method on the standard input handle to get `input` from the user\n\nThe `\u0026` indicates that this argument is a `reference`, which gives you a way to let multiple parts of your code access one piece of data without needing to copy that data into memory multiple times.\n\n### Handling Potential Failure with Result\n`One long line` is difficult to read, so it’s best to `divide` it\nThe next part is this method\n```rust\n        .expect(\"Failed to read line\");\n```\nAs mentioned earlier, `read_line` puts whatever the user enters into the string we pass to it, but it also returns a `Result` value - `enum`.\nResult’s variants are `Ok` and `Err`.\nAn instance of `Result` has an `expect` method:\n- if `Err` value, expect will cause the program to crash and display message  \n- if `Ok` value, expect will take the return value and return just it  \n\u003e If you don’t call `expect`, the program will compile, but you’ll get a `warning`\n\n### Printing Values with println! Placeholders\nThere’s only one more line to discuss in the code so far:\n ```rust\n     println!(\"You guessed: {guess}\");\n```\n\u003e The `{}` set of curly brackets is a `placeholder`: think of {} as little crab pincers that hold a value in place.\n\nPrinting a variable and the result of an expression in one call to println! would look like this:\n```rust\nlet x = 5;\nlet y = 10;\n\nprintln!(\"x = {x} and y + 2 = {}\", y + 2); // \"x = 5 and y = 12\"\n```\n### Testing the First Part\nLet’s test the first part of the guessing game.\n```sh\ncargo run\n```\n\n## Generating a Secret Number\nNext, we need to generate a secret number that the user will try to guess.\n\n### Using a Crate to Get More Functionality\nThe `rand` crate is a library crate, which contains code that is intended\n```sh\n[dependencies]\nrand = \"0.8.5\"\n```\n\u003e The specifier 0.8.5 is actually shorthand for ^0.8.5, which means any version that is at least 0.8.5 but below 0.9.0.\n\n### Ensuring Reproducible Builds with the Cargo.lock File\nWhen you `build` a project for the `first time`, Cargo figures out all the versions of the dependencies that fit the criteria and then writes them to the `Cargo.lock` file. \n\n### Updating a Crate to Get a New Version\nWhen you do want to update a crate, Cargo provides the `command update`, which will ignore the `Cargo.lock` file and figure out all the latest versions that fit your specifications in Cargo.toml. \n```sh\ncargo update\n```\n\n### Generating a Random Number\nLet’s start using rand to generate a number to guess.\n```rust\nuse std::io;\nuse rand::Rng; //trait defines methods that random number generators implement\n\nfn main() {\n    println!(\"Guess the number!\");\n\n    let secret_number = rand::thread_rng().gen_range(1..=100);\n\n    println!(\"The secret number is: {secret_number}\");\n\n    println!(\"Please input your guess.\");\n\n    let mut guess = String::new();\n\n    io::stdin()\n        .read_line(\u0026mut guess)\n        .expect(\"Failed to read line\");\n\n    println!(\"You guessed: {guess}\");\n}\n```\n\u003e Another neat feature of Cargo is that running the `cargo doc --open` command will build documentation provided by all your dependencies locally and open it in your browser\n\nWe call the `rand::thread_rng` function that gives us the particular random number generator we’re going to use: one that is local to the current thread of execution and is seeded by the operating system. Then we call the `gen_range` method on the random number generator. This method is defined by the `Rng trait` that we brought into scope with the `use rand::Rng;` statement. \n\n## Comparing the Guess to the Secret Number\nNow that we have user input and a random number, we can compare them. \n```rust\nuse rand::Rng;\nuse std::cmp::Ordering; \nuse std::io;\n\nfn main() {\n    // --snip--\n\n    println!(\"You guessed: {guess}\");\n\n    match guess.cmp(\u0026secret_number) {\n        Ordering::Less =\u003e println!(\"Too small!\"),\n        Ordering::Greater =\u003e println!(\"Too big!\"),\n        Ordering::Equal =\u003e println!(\"You win!\"),\n    }\n}\n```\nFirst we add another use statement, bringing a type called `std::cmp::Ordering` into scope from the standard library. The Ordering type is another `enum` and has the variants `Less, Greater, and Equal`.\n\nThe `cmp` method compares two values and can be called on anything that can be compared. It takes a `reference` to whatever you want to compare with: here it’s comparing `guess` to `secret_number`. \n\nWe use a `match` expression to decide what to do next based on which variant of `Ordering` was returned from the call to `cmp` with the values in `guess` and `secret_number`.\n\n\u003e The core of the error states that there are `mismatched types`. Rust has a strong, static type system. However, it also has type inference. When we wrote `let mut guess = String::new()`, Rust was able to infer that guess should be a `String` and didn’t make us write the type.\n\nUltimately, we want to `convert` the `String` the program reads as input into a `real number type` so we can compare it numerically to the secret number:\n```rust\n    // --snip--\n    let mut guess = String::new();\n    io::stdin()\n        .read_line(\u0026mut guess)\n        .expect(\"Failed to read line\");\n    let guess: u32 = guess.trim().parse().expect(\"Please type a number!\"); //convert str to u32\n    println!(\"You guessed: {guess}\");\n    match guess.cmp(\u0026secret_number) {\n        Ordering::Less =\u003e println!(\"Too small!\"),\n        Ordering::Greater =\u003e println!(\"Too big!\"),\n        Ordering::Equal =\u003e println!(\"You win!\"),\n    }\n```\n\u003e Rust allows us to `shadow` the previous value of guess with a new one. `Shadowing` lets us `reuse` the guess variable name rather than forcing us to create two unique variables, such as `guess_str` and `guess`\n\nThe `parse` method on strings converts a string to `another type`. Here, we use it to convert from a string to a `number`. We need to tell Rust the exact number type we want by using `let guess: u32`.\n\n## Allowing Multiple Guesses with Looping\nThe loop keyword creates an infinite loop.\n```rust\n    // --snip--\n    println!(\"The secret number is: {secret_number}\");\n    loop {\n        println!(\"Please input your guess.\");\n        // --snip--\n        match guess.cmp(\u0026secret_number) {\n            Ordering::Less =\u003e println!(\"Too small!\"),\n            Ordering::Greater =\u003e println!(\"Too big!\"),\n            Ordering::Equal =\u003e println!(\"You win!\"),\n        }\n    }\n}\n```\n### Handling Invalid Input\nWe switch from an expect call to a match expression to move from crashing on an error to handling the error.\n```rust\n        // --snip--\n        io::stdin()\n            .read_line(\u0026mut guess)\n            .expect(\"Failed to read line\");\n        let guess: u32 = match guess.trim().parse() {\n            Ok(num) =\u003e num,\n            Err(_) =\u003e continue,\n        };\n        println!(\"You guessed: {guess}\");\n        // --snip--\n```\n\n## Summary\nThis project was a hands-on way to introduce you to many new Rust concepts: let, match, functions, the use of external crates, and more.\n\n# 3 Common Programming Concepts\nThis chapter covers concepts that appear in almost every programming language and how they work in Rust.\n\n## Variables and Mutability\nBy default, variables are `immutable`\nWhen a variable is immutable, once a value is bound to a name, you `can’t change` that value.\n```rust\nfn main() {\n    let x = 5;\n    println!(\"The value of x is: {x}\");\n    x = 6;\n    println!(\"The value of x is: {x}\");\n}\n```\nAlthough variables are immutable by default, you can make them mutable by adding `mut` in front of the variable name \n```rust\nfn main() {\n    let mut x = 5;\n    println!(\"The value of x is: {x}\");\n    x = 6;\n    println!(\"The value of x is: {x}\");\n}\n```\n\n### Constants\nLike `immutable variables`, constants are values that are bound to a name and `are not allowed to change`, but there are a few `differences` between constants and variables.\n- `aren’t allowed to use mut` with constants.\n- may be set only to a `constant expression`, not the result of a value that could only be computed at runtime.\n```rust\nconst THREE_HOURS_IN_SECONDS: u32 = 60 * 60 * 3;\n```\nRust’s naming convention for constants is to use `all uppercase with underscores` between words\n\n### Shadowing\nYou can declare a new variable with `the same name` as a previous variable - the first variable is `shadowed` by the second\nWe can shadow a variable by using the same variable’s name and repeating the use of the `let` keyword as follows\n```rust\nfn main() {\n    let x = 5;\n    let x = x + 1;\n    {\n        let x = x * 2;\n        println!(\"The value of x in the inner scope is: {x}\");\n    }\n    println!(\"The value of x is: {x}\");\n}\n```\n\nShadowing is `different` from marking a variable as `mut` because\n- we’ll get a compile-time error if we accidentally try to reassign to this variable without using the `let` keyword\n- we’re effectively creating a new variable when we use the `let` keyword again, we can change the type of the value but reuse the same name\n```rust\n    let spaces = \"   \"; // str\n    let spaces = spaces.len(); // int\n```\n\n## Data Types\nEvery value in Rust is of a certain `data type`, which tells Rust what kind of data is being specified so it knows how to work with that data. \nKeep in mind that Rust is a `statically typed language`\n```rust\nlet guess: u32 = \"42\".parse().expect(\"Not a number!\");\n```\n\n### Scalar Types\nA scalar type represents a single value. Rust has four primary scalar types: \n- integers  \n- floating point numbers  \n- booleans  \n- characters  \n\n### Integer Types\nAn integer is a number without a fractional component `i8 i16 i32 i64 i128`, `u8 u16 u32 u64 u128`\nthe `isize` and `usize` types depend on the architecture of the computer \n\n### Floating-Point Types\nRust also has two primitive types for floating-point numbers, which are numbers with decimal points. Rust’s floating-point types are `f32` and `f64`\n```rust\nfn main() {\n    let x = 2.0; // f64\n    let y: f32 = 3.0; // f32\n}\n```\n\n### Numeric Operations\n```rust\nfn main() {\n    // addition\n    let sum = 5 + 10;\n    // subtraction\n    let difference = 95.5 - 4.3;\n    // multiplication\n    let product = 4 * 30;\n    // division\n    let quotient = 56.7 / 32.2;\n    let truncated = -5 / 3; // Results in -1\n    // remainder\n    let remainder = 43 % 5;\n}\n```\n\n### The Boolean Type\nAs in most other programming languages, a Boolean type in Rust has two possible values: `true` and `false`.\n```rust\nfn main() {\n    let t = true;\n    let f: bool = false; // with explicit type annotation\n}\n```\n\n### The Character Type\nRust’s `char` type is the language’s most primitive alphabetic type.\n```rust\nfn main() {\n    let c = 'z';\n    let z: char = 'ℤ'; // with explicit type annotation\n    let heart_eyed_cat = '😻';\n}\n```\n\n### Compound Types\nCompound types can group multiple values into one type. Rust has two primitive compound types: `tuples` and `arrays`.\n\n### The Tuple Type\nA `tuple` is a general way of grouping together a number of values with a variety of types into `one` compound type. \n```rust\nfn main() {\n    let tup: (i32, f64, u8) = (500, 6.4, 1);\n}\n```\nThe variable tup binds to the entire tuple because a tuple is considered a single compound element. To get the individual values out of a tuple, we can use pattern matching to destructure a tuple value, like this:\n```rust\nfn main() {\n    let tup = (500, 6.4, 1);\n    let (x, y, z) = tup;\n    println!(\"The value of y is: {y}\");\n}\n```\nWe can also access a tuple element directly by using a period `(.)` followed by the index of the value we want to access\n```rust\nfn main() {\n    let x: (i32, f64, u8) = (500, 6.4, 1);\n    let five_hundred = x.0;\n    let six_point_four = x.1;\n    let one = x.2;\n}\n```\nThe tuple without any values has a special name, `unit`.\n\n### The Array Type\nUnlike a tuple, every element of an array must have the `same type`. Unlike arrays in some other languages, arrays in Rust have a `fixed length`.\n```rust\nfn main() {\n    let a = [1, 2, 3, 4, 5];\n    let a: [i32; 5];\n    let a = [3; 5];\n}\n```\nA `vector` is a similar collection type provided by the standard library that is allowed to `grow or shrink` in size\n\n### Accessing Array Elements\nAn array is a single chunk of memory of a known, `fixed` size that can be `allocated` on the `stack`. You can access elements of an array using `indexing`\n```rust\nfn main() {\n    let a = [1, 2, 3, 4, 5];\n    let first = a[0];\n    let second = a[1];\n}\n```\n\n### Invalid Array Element Access\nRust will `check` that the index you’ve specified is `less than` the array `length`. If the index is greater than or equal to the length, Rust will `panic`. \nThis is an example of Rust’s memory `safety principles` in action. In many low-level languages, this kind of check is not done, and when you provide an `incorrect` index, invalid memory `can be accessed`. \n\n## Functions\n`main` function, which is the `entry point` of many programs. You’ve also seen the `fn` keyword, which allows you to declare new functions.\nRust code uses `snake case` as the conventional `style` for function and variable names, in which all letters are lowercase and underscores separate words\n```rust\nfn main() {\n    println!(\"Hello, world!\");\n    another_function();\n}\nfn another_function() {\n    println!(\"Another function.\");\n}\n```\n\n### Parameters\nWe can define functions to have `parameters`\n```rust\nfn main() {\n    another_function(5);\n}\nfn another_function(x: i32) { //The type of x is specified as i32\n    println!(\"The value of x is: {x}\");\n}\n```\nIn function signatures, you must declare the `type` of each `parameter`\nWhen defining `multiple parameters`, separate the parameter declarations with `commas`\n\n### Statements and Expressions\nRust is an `expression-based` language\n- Statements are instructions that perform some action and do not return a value  \n- Expressions evaluate to a resultant value  \n\nCreating a variable and assigning a value to it with the let keyword is a statement\n```rust\nfn main() {\n    let y = 6;\n}\n```\n\nStatements do not return values. Therefore, you `can’t assign a let` statement to another variable, as the following code tries to do; you’ll get an `error`\n```rust\nfn main() {\n    let x = (let y = 6);\n}\n```\nThe `let y = 6` statement does `not return` a value, so there isn’t anything for `x` to bind to\n`Expressions` evaluate to a value and make up most of the `rest of the code` that you’ll write in Rust. Calling a function is an expression. Calling a macro is an expression. A new scope block created with curly brackets is an expression\n\n\n`Expressions` do not include `ending semicolons`. If you `add a semicolon` to the end of an expression, you `turn` it into a `statement`, and it will then not return a value.\n```rust\n{\n    let x = 3;\n    x + 1\n}\n```\n\n### Functions with Return Values\nWe `don’t name` return values, but we must `declare` their `type` after an arrow `(-\u003e)`.\nIn Rust, the `return value` of the function is synonymous with the value of the `final expression` in the block of the body of a function.\nYou can return `early` from a function by using the `return`\n```rust\nfn five() -\u003e i32 { // declare only return Type\n    5 // no ; or return word\n}\n```\n\nBut if we place a `semicolon` at the end of the line containing x + 1, `changing` it from an `expression` to a `statement` - wll be error statements don’t evaluate to a value, which is expressed by (), the unit type\n```rust\nfn plus_one(x: i32) -\u003e i32 {\n    x + 1; // error here, return unit type - ()\n}\n```\n\n## Comments\n```rust\n// So we’re doing something complicated here, long enough that we need\n// multiple lines of comments to do it! Whew! Hopefully, this comment will\n// explain what’s going on.\n\nfn main() {\n    // I’m feeling lucky today\n    let lucky_number = 7;\n}\n```\n\n## Control Flow\nThe most common constructs that let you control the flow of execution of Rust code are `if` expressions and `loops`.\n\n### if Expressions\n```rust\nfn main() {\n    let number = 3;\n    if number \u003c 5 {\n        println!(\"condition was true\");\n    } else {\n        println!(\"condition was false\");\n    }\n}\n```\n Unlike languages such as Ruby and JavaScript, Rust will `not automatically` try to `convert` `non-Boolean` types `to a Boolean`. You must be `explicit` and always provide if with a `Boolean as its condition`.\n ```rust\n fn main() {\n    let number = 3;\n    if number != 0 {\n        println!(\"number was something other than zero\");\n    }\n}\n``` \n\n### Handling Multiple Conditions with else if\nUsing `too many else if` expressions can `clutter` your code, so if you have more than one - use `match`\n\n### Using if in a let Statement\nBecause `if` is an `expression`, we can use it on the `right side` of a `let` statement to assign the outcome to a variable\n```rust\nfn main() {\n    let condition = true;\n    let number = if condition { 5 } else { 6 };\n    println!(\"The value of number is: {number}\");\n}\n```\n\n## Repetition with Loops\n\nRust has three kinds of loops: `loop`, `while`, and `for`. Let’s try each one.\n\n### Repeating Code with loop\nYou can place the `break` keyword within the loop to tell the program when to stop \nWe also used `continue` in the guessing game, which in a loop tells the program to skip over any remaining code in this iteration of the loop and go to the next iteration.\n\n### Returning Values from Loops\nYou can `add the value` you want returned `after the break` expression you use to stop the loop\n```rust\nfn main() {\n    let mut counter = 0;\n    let result = loop {\n        counter += 1;\n        if counter == 10 {\n            break counter * 2;\n        }\n    };\n    println!(\"The result is {result}\");\n}\n```\n\n### Loop Labels to Disambiguate Between Multiple Loops\nYou can optionally specify a loop `label` on a loop that you can then use with `break` or `continue`\n```rust\nfn main() {\n    let mut count = 0;\n    'counting_up: loop {\n        println!(\"count = {count}\");\n        let mut remaining = 10;\n        loop {\n            println!(\"remaining = {remaining}\");\n            if remaining == 9 {\n                break; // break internal loop\n            }\n            if count == 2 {\n                break 'counting_up; // break external loop\n            }\n            remaining -= 1;\n        }\n        count += 1;\n    }\n    println!(\"End count = {count}\");\n}\n```\n\n### Conditional Loops with while\nA program will `often need` to evaluate a `condition` within a loop. While the condition is true, the loop runs.\n```rust\nfn main() {\n    let mut number = 3;\n    while number != 0 {\n        println!(\"{number}!\");\n        number -= 1;\n    }\n    println!(\"LIFTOFF!!!\");\n}\n```\n\n### Looping Through a Collection with for\nYou can use a `for` loop and execute some code for `each item` in a `collection`.\n```rust\nfn main() {\n    let a = [10, 20, 30, 40, 50];\n    for element in a {\n        println!(\"the value is: {element}\");\n    }\n}\n```\n\n# 4 Ownership  \n\n## What is Ownership  \nOwnership is a set of rules that govern how a Rust program `manages` memory.\n\n### The Stack and the Heap  \nThe `stack` stores values in the order it gets them and removes the values in the opposite order - `last in, first out`.\nLike plates. Adding or removing plates from the middle or bottom wouldn’t work as well! Adding data is called pushing onto the stack, and removing data is called popping off the stack.\n\nThe `heap` is less organized: when you put data on the heap, you request a certain amount of space. The memory allocator finds an empty spot in the heap that is big enough, marks it as being in use, and returns a pointer, which is the address of that location - `allocating`\nLike Restaurant. When you enter, you state the number of people in your group, and the host finds an empty table that fits everyone and leads you there. If someone in your group comes late, they can ask where you’ve been seated to find you.\n\n### Ownership Rules  \n- Each value in Rust has an owner  \n- There can only be one owner at a time  \n- When the owner goes out of scope, the value will be dropped  \n\n### Variable Scope\n```rust\nfn main() {\n    {                      // s is not valid here, it’s not yet declared\n        let s = \"hello\";   // s is valid from this point forward\n        // do stuff with s\n    }                      // this scope is now over, and s is no longer valid\n}\n```\n\n### The String Type\nRust has a second string type `String`  \nThis type manages data allocated on the heap and as such is able to store an amount of text that is unknown to us at compile time.  \n```rust\nfn main() {\n    let mut s = String::from(\"hello\");\n\n    s.push_str(\", world!\"); // push_str() appends a literal to a String\n\n    println!(\"{}\", s); // This will print `hello, world!`\n}\n```\n\n### Memory and Allocation\nWith the String type, in order to support a mutable, growable piece of text, we need to allocate an amount of memory on the heap, unknown at compile time, to hold the contents. This means:  \n- The memory must be requested from the memory allocator at runtime.  \n- We need a way of returning this memory to the allocator when we’re done with our String.  \n\nThe memory is automatically returned `drop` once the variable that owns it goes `out of scope`. \n```rust\nfn main() {\n    {\n        let s = String::from(\"hello\"); // s is valid from this point forward\n        // do stuff with s\n    }                                  // this scope is now over, and s is no\n                                       // longer valid\n}\n```\n\n### Variables and Data Interacting with Move\nTo ensure memory safety, after the line `let s2 = s1;`, Rust considers `s1` as no longer valid. Therefore, Rust doesn’t need to `free anything` when s1 goes out of scope. \n```rust\nfn main() {\n    let s1 = String::from(\"hello\");\n    let s2 = s1;\n\n    println!(\"{}, world!\", s1);\n}\n```\nInstead of being called a shallow copy, it’s known as a `move`. In this example, we would say that `s1 was moved into s2`.\n\n### Variables and Data Interacting with Clone\nIf we do want to `deeply copy` the heap data of the String, not just the stack data, we can use a common method called `clone`.\n```rust\nfn main() {\n    let s1 = String::from(\"hello\");\n    let s2 = s1.clone();\n\n    println!(\"s1 = {}, s2 = {}\", s1, s2);\n}\n```\n\n### Stack-Only Data: Copy\nIntegers that `have a known size at compile time` are stored entirely on the `stack`, so copies of the actual values are quick to make.\n```rust\nfn main() {\n    let x = 5;\n    let y = x;\n\n    println!(\"x = {}, y = {}\", x, y);\n}\n```\n\nTypes implement the `Copy`   \n- All the integer types, such as u32.  \n- The Boolean type, bool, with values true and false.  \n- All the floating-point types, such as f64.  \n- The character type, char.  \n- Tuples, if they only contain types that also implement Copy. For example, (i32, i32) implements Copy, but (i32, String) does not.  \n\n### Ownership and Functions\nThe mechanics of passing a value to a function `are similar to those when assigning a value to a variable`. Passing a variable to a function will `move or copy`, just as assignment does.  \n```rust\nfn main() {\n    let s = String::from(\"hello\");  // s comes into scope\n\n    takes_ownership(s);             // s's value moves into the function...\n                                    // ... and so is no longer valid here\n\n    let x = 5;                      // x comes into scope\n\n    makes_copy(x);                  // x would move into the function,\n                                    // but i32 is Copy, so it's okay to still\n                                    // use x afterward\n\n} // Here, x goes out of scope, then s. But because s's value was moved, nothing\n  // special happens.\n\nfn takes_ownership(some_string: String) { // some_string comes into scope\n    println!(\"{}\", some_string);\n} // Here, some_string goes out of scope and `drop` is called. The backing\n  // memory is freed.\n\nfn makes_copy(some_integer: i32) { // some_integer comes into scope\n    println!(\"{}\", some_integer);\n} // Here, some_integer goes out of scope. Nothing special happens.\n```\n\n### Return Values and Scope\nReturning values can also `transfer ownership`.\n```rust\nfn main() {\n    let s1 = gives_ownership();         // gives_ownership moves its return\n                                        // value into s1\n\n    let s2 = String::from(\"hello\");     // s2 comes into scope\n\n    let s3 = takes_and_gives_back(s2);  // s2 is moved into\n                                        // takes_and_gives_back, which also\n                                        // moves its return value into s3\n} // Here, s3 goes out of scope and is dropped. s2 was moved, so nothing\n  // happens. s1 goes out of scope and is dropped.\n\nfn gives_ownership() -\u003e String {             // gives_ownership will move its\n                                             // return value into the function\n                                             // that calls it\n\n    let some_string = String::from(\"yours\"); // some_string comes into scope\n\n    some_string                              // some_string is returned and\n                                             // moves out to the calling\n                                             // function\n}\n\n// This function takes a String and returns one\nfn takes_and_gives_back(a_string: String) -\u003e String { // a_string comes into\n                                                      // scope\n\n    a_string  // a_string is returned and moves out to the calling function\n}\n```\n\n## References and Borrowing\n\nA `reference` is like a `pointer` in that it’s an address we can follow to access the data stored at that address.\nFunction that has a `reference to an object as a parameter instead` of taking ownership of the value\n```rust\nfn main() {\n    let s1 = String::from(\"hello\");\n\n    let len = calculate_length(\u0026s1);\n\n    println!(\"The length of '{}' is {}.\", s1, len);\n}\n\nfn calculate_length(s: \u0026String) -\u003e usize {\n    s.len()\n}\n```\n\nPass `\u0026s1` into `calculate_length` and, in its definition, we take `\u0026String` rather than `String`.\n\u003eThe opposite of referencing by using `\u0026` is dereferencing, which is accomplished with the dereference operator, `*`.  \n\nWe call the action of creating a reference `borrowing`. As in real life, if a person owns something, you can borrow it from them. When you’re done, you have to give it back. `You don’t own it`.  \n\nJust as variables are immutable by default, so are references. We’re not allowed to modify something we have a reference to.\n\n### Mutable References\nFirst we change `s` to be `mut`. Then we create a mutable reference with `\u0026mut` s where we call the change function, and update the function signature to accept a mutable reference with `some_string: \u0026mut String`. This makes it very clear that the change function will `mutate the value it borrows`.\n```rust\nfn main() {\n    let mut s = String::from(\"hello\");\n\n    change(\u0026mut s);\n}\n\nfn change(some_string: \u0026mut String) {\n    some_string.push_str(\", world\");\n}\n```\n\u003e Mutable references have one big restriction: if you have a mutable reference to a value, you `can have no other references to that value` - `data races`\n\nRust enforces a similar rule for combining mutable and immutable references. \n```rust\nfn main() {\n    let mut s = String::from(\"hello\");\n\n    let r1 = \u0026s; // no problem\n    let r2 = \u0026s; // no problem\n    let r3 = \u0026mut s; // BIG PROBLEM\n\n    println!(\"{}, {}, and {}\", r1, r2, r3);\n}\n```\n\nThe scopes of the immutable references `r1` and `r2` end after the `println!` where they are last used, which is before the mutable reference `r3` is created.\n```rust\nfn main() {\n    let mut s = String::from(\"hello\");\n\n    let r1 = \u0026s; // no problem\n    let r2 = \u0026s; // no problem\n    println!(\"{} and {}\", r1, r2);\n    // variables r1 and r2 will not be used after this point\n\n    let r3 = \u0026mut s; // no problem\n    println!(\"{}\", r3);\n}\n```\n\n### Dangling References\nIn languages with pointers, it’s easy to erroneously create a `dangling pointer` — a pointer that references a location in memory that may `have been given to someone else` — by freeing some memory while preserving a pointer to that memory.\n```rust\nfn main() {\n    let reference_to_nothing = dangle();\n}\n\nfn dangle() -\u003e \u0026String { // dangle returns a reference to a String\n\n    let s = String::from(\"hello\"); // s is a new String\n\n    \u0026s // we return a reference to the String, s\n} // Here, s goes out of scope, and is dropped. Its memory goes away.\n  // Danger!\n```\n\nThe solution here is to return the `String` directly:\n```rust\nfn main() {\n    let string = no_dangle();\n}\n\nfn no_dangle() -\u003e String {\n    let s = String::from(\"hello\");\n\n    s\n}\n```\n\n### The Rules of References  \nLet’s recap what we’ve discussed about references:  \n- At any given time, you can have either one mutable reference or any number of immutable references.  \n- References must always be valid.  \n\n### The Slice Type\nSlices let you reference a contiguous sequence of elements in a collection rather than the whole collection. A slice is a kind of `reference`, so it does not have `ownership`.\n\nThe problem: Having to worry about the index in word getting out of sync with the data in s is tedious and error prone!\n```rust\nfn first_word(s: \u0026String) -\u003e usize {\n    let bytes = s.as_bytes();\n\n    for (i, \u0026item) in bytes.iter().enumerate() {\n        if item == b' ' {\n            return i;\n        }\n    }\n\n    s.len()\n}\n\nfn main() {\n    let mut s = String::from(\"hello world\");\n\n    let word = first_word(\u0026s); // word will get the value 5\n\n    s.clear(); // this empties the String, making it equal to \"\"\n\n    // word still has the value 5 here, but there's no more string that\n    // we could meaningfully use the value 5 with. word is now totally invalid!\n}\n```\n \n ### String Slices\n A string slice is a `reference to part of a String`, and it looks like this:\n```rust\n fn main() {\n    let s = String::from(\"hello world\");\n\n    let hello = \u0026s[0..5];\n    let world = \u0026s[6..11];\n\tlet slice = \u0026s[..2]; //if you want to start at index 0\n\tlet slice = \u0026s[3..]; //if your slice includes the last byte\n\tlet slice = \u0026s[..]; //entire slice\n\n}\n```\n\nRecall from the borrowing rules that if we have an immutable reference to something, we cannot also take a `mutable reference`. Because `clear` needs to truncate the `String`, it needs to get a `mutable reference`. The `println!` after the call to clear uses the reference in word, so the `immutable reference must still be active at that point`. Rust disallows the mutable reference in clear and the immutable reference in word from `existing at the same time`, and compilation fails.\n```rust\nfn first_word(s: \u0026String) -\u003e \u0026str {\n    let bytes = s.as_bytes();\n\n    for (i, \u0026item) in bytes.iter().enumerate() {\n        if item == b' ' {\n            return \u0026s[0..i];\n        }\n    }\n\n    \u0026s[..]\n}\n\nfn main() {\n    let mut s = String::from(\"hello world\");\n\n    let word = first_word(\u0026s);\n\n    s.clear(); // error!\n\n    println!(\"the first word is: {}\", word);\n}\n```\n\n### String Slices as Parameters\nKnowing that you can take slices of literals and String values leads us to one more improvement on first_word, and that’s its signature:\n```rust\nfn first_word(s: \u0026String) -\u003e \u0026str {\n```\nA more experienced Rustacean would write the signature shown in Listing 4-9 instead because it allows us to use the same function on both \u0026String values and \u0026str values.\n```rust\nfn first_word(s: \u0026str) -\u003e \u0026str {\n```\n\n### Other Slices\nJust as we might want to refer to part of a string, we might want to refer to part of an array\n```rust\n#![allow(unused)]\nfn main() {\nlet a = [1, 2, 3, 4, 5];\n\nlet slice = \u0026a[1..3];\n\nassert_eq!(slice, \u0026[2, 3]);\n}\n```\n\n## Summary\nThe concepts of ownership, borrowing, and slices ensure memory safety in Rust programs at compile time. The Rust language gives you control over your memory usage in the same way as other systems programming languages, but having the owner of data automatically clean up that data when the owner goes out of scope means you don’t have to write and debug extra code to get this control.\n\n\n# 5 Using Structs\n\n## Defining and Instantiating Structs\n\nA `struct, or structure`, is a custom data type that lets you package together and name multiple related values that make up a meaningful group. \n```rust\nstruct User {\n    active: bool,\n    username: String,\n    email: String,\n    sign_in_count: u64,\n}\n\nfn main() {}\n```\n\nTo get a specific value from a struct, we use dot notation.\n```rust\nfn main() {\n    let mut user1 = User {\n        active: true,\n        username: String::from(\"someusername123\"),\n        email: String::from(\"someone@example.com\"),\n        sign_in_count: 1,\n    };\n\n    user1.email = String::from(\"anotheremail@example.com\");\n}\n```\n\n### Using the Field Init Shorthand\n\nBecause the parameter names and the struct field names are exactly the same in we can use the field init shorthand syntax\n```rust\nfn build_user(email: String, username: String) -\u003e User {\n    User {\n        active: true,\n        username,\n        email,\n        sign_in_count: 1,\n    }\n}\n```\n\n### Creating Instances from Other Instances with Struct Update Syntax\n\nIt’s often useful to create a new instance of a struct that includes most of the values from another instance, but changes some. You can do this using `struct update syntax`. The syntax `..` specifies that the remaining fields not explicitly set should have the same value as the fields in the given instance.\n```rust\nfn main() {\n    // --snip--\n\n    let user2 = User {\n        email: String::from(\"another@example.com\"),\n        ..user1\n    };\n}\n```\n\n### Using Tuple Structs Without Named Fields to Create Different Types\nRust also supports structs that look similar to tuples, called `tuple structs`.\n```rust\nstruct Color(i32, i32, i32);\nstruct Point(i32, i32, i32);\n\nfn main() {\n    let black = Color(0, 0, 0);\n    let origin = Point(0, 0, 0);\n}\n```\n\n### Unit-Like Structs Without Any Fields\nYou can also define structs that don’t have any fields! \n```rust\nstruct AlwaysEqual;\n\nfn main() {\n    let subject = AlwaysEqual;\n}\n```\n\n### Ownership of Struct Data\n\n\u003e In the User struct definition in Listing 5-1, we used the owned String type rather than the \u0026str string slice type. This is a deliberate choice because we want each instance of this struct to own all of its data and for that data to be valid for as long as the entire struct is valid.  \n\n## An Example Program Using Structs\nTo understand when we might want to use structs, let’s write a program that calculates the area of a rectangle. We’ll start by using single variables, and then refactor the program until we’re using structs instead.\n```rust\nfn main() {\n    let width1 = 30;\n    let height1 = 50;\n\n    println!(\n        \"The area of the rectangle is {} square pixels.\",\n        area(width1, height1)\n    );\n}\n\nfn area(width: u32, height: u32) -\u003e u32 {\n    width * height\n}\n```\n\n### Refactoring with Tuples\nIn one way, this program is better. Tuples let us add a bit of structure, and we’re now passing just one argument. But in another way, this version is less clear: tuples don’t name their elements, so we have to index into the parts of the tuple, making our calculation less obvious.\n```rust\nfn main() {\n    let rect1 = (30, 50);\n\n    println!(\n        \"The area of the rectangle is {} square pixels.\",\n        area(rect1)\n    );\n}\n\nfn area(dimensions: (u32, u32)) -\u003e u32 {\n    dimensions.0 * dimensions.1\n}\n```\n\n### Refactoring with Structs: Adding More Meaning\nWe use structs to add meaning by labeling the data. We can transform the tuple we’re using into a struct with a name for the whole as well as names for the parts\n```rust\nstruct Rectangle {\n    width: u32,\n    height: u32,\n}\n\nfn main() {\n    let rect1 = Rectangle {\n        width: 30,\n        height: 50,\n    };\n\n    println!(\n        \"The area of the rectangle is {} square pixels.\",\n        area(\u0026rect1)\n    );\n}\n\nfn area(rectangle: \u0026Rectangle) -\u003e u32 {\n    rectangle.width * rectangle.height\n}\n```\n\n### Adding Useful Functionality with Derived Traits\nRust does include functionality to print out debugging information, but we have to explicitly opt in to make that functionality available for our struct. To do that, we add the outer attribute `#[derive(Debug)]` just before the struct definition\n```rust\n#[derive(Debug)]\nstruct Rectangle {\n    width: u32,\n    height: u32,\n}\n\nfn main() {\n    let rect1 = Rectangle {\n        width: 30,\n        height: 50,\n    };\n\n    println!(\"rect1 is {:?}\", rect1); // {:?} used for print debug info\n}\n```\n\nAnother way to print out a value using the `Debug` format is to use the `dbg! macro`\n```rust\n#[derive(Debug)]\nstruct Rectangle {\n    width: u32,\n    height: u32,\n}\n\nfn main() {\n    let scale = 2;\n    let rect1 = Rectangle {\n        width: dbg!(30 * scale),\n        height: 50,\n    };\n\n    dbg!(\u0026rect1);\n}\n```\n\n## Method Syntax\n`Methods` are similar to functions: we declare them with the fn keyword and a name, they can have parameters and a return value, and they contain some code that’s run when the method is called from somewhere else. \n\n### Defining Methods\nLet’s change the area function that has a `Rectangle` instance as a parameter and instead make an `area` method defined on the `Rectangle struct`.\nTo define the function within the context of `Rectangle`, we start an `impl` (implementation) block for Rectangle. Everything within this impl block will be `associated` with the Rectangle type\n```rust\n#[derive(Debug)]\nstruct Rectangle {\n    width: u32,\n    height: u32,\n}\n\nimpl Rectangle {\n    fn area(\u0026self) -\u003e u32 {\n        self.width * self.height\n    }\n}\n\nfn main() {\n    let rect1 = Rectangle {\n        width: 30,\n        height: 50,\n    };\n\n    println!(\n        \"The area of the rectangle is {} square pixels.\",\n        rect1.area()\n    );\n}\n```\nIn the signature for area, we use `\u0026self` instead of `rectangle: \u0026Rectangle`. The `\u0026self` is actually short for `self: \u0026Self`. Within an `impl` block, the type Self is an `alias` for the type that the impl block is for. \n\nMethods like this are called `getters`, and Rust does not implement them automatically for struct fields as some other languages do.\n```rust\nimpl Rectangle {\n    fn width(\u0026self) -\u003e bool {\n        self.width \u003e 0\n    }\n}\n\nfn main() {\n    let rect1 = Rectangle {\n        width: 30,\n        height: 50,\n    };\n\n    if rect1.width() {\n        println!(\"The rectangle has a nonzero width; it is {}\", rect1.width);\n    }\n}\n```\n\n### Where’s the -\u003e Operator?\n\u003e In C and C++, two different operators are used for calling methods: you use `.` if you’re calling a method on the object directly and `-\u003e` if you’re calling the method on a pointer to the object and need to dereference the pointer first. In other words, if `object` is a pointer, `object-\u003esomething()` is similar to `(*object).something()`.\nRust doesn’t have an equivalent to the `-\u003e operator;` instead, Rust has a feature called `automatic referencing and dereferencing`. Calling methods is one of the few places in Rust that has this behavior.\n\n### Methods with More Parameters\nLet’s practice using methods by implementing a second method on the `Rectangle` struct. This time we want an instance of Rectangle to take another instance of Rectangle and return `true` if the second Rectangle can fit completely within `self` (the first Rectangle); otherwise, it should return `false`.\n```rust\n#[derive(Debug)]\nstruct Rectangle {\n    width: u32,\n    height: u32,\n}\n\nimpl Rectangle {\n    fn area(\u0026self) -\u003e u32 {\n        self.width * self.height\n    }\n\n    fn can_hold(\u0026self, other: \u0026Rectangle) -\u003e bool {\n        self.width \u003e other.width \u0026\u0026 self.height \u003e other.height\n    }\n}\n\nfn main() {\n    let rect1 = Rectangle {\n        width: 30,\n        height: 50,\n    };\n    let rect2 = Rectangle {\n        width: 10,\n        height: 40,\n    };\n    let rect3 = Rectangle {\n        width: 60,\n        height: 45,\n    };\n\n    println!(\"Can rect1 hold rect2? {}\", rect1.can_hold(\u0026rect2));\n    println!(\"Can rect1 hold rect3? {}\", rect1.can_hold(\u0026rect3));\n}\n```\n\n### Associated Functions\nAll functions defined within an `impl` block are called `associated functions because` they’re associated with the type named after the impl. We can define associated functions that `don’t have self` as their first parameter (and thus are not methods) because they `don’t need an instance` of the type to work with. We’ve already used one function like this: the `String::from` function that’s defined on the String type.\n```rust\n#[derive(Debug)]\nstruct Rectangle {\n    width: u32,\n    height: u32,\n}\n\nimpl Rectangle {\n    fn square(size: u32) -\u003e Self {\n        Self {\n            width: size,\n            height: size,\n        }\n    }\n}\n\nfn main() {\n    let sq = Rectangle::square(3); // call this associated function\n}\n```\n\n### Multiple impl Blocks\nEach struct is allowed to have `multiple impl` blocks. \n```rust\nimpl Rectangle {\n    fn area(\u0026self) -\u003e u32 {\n        self.width * self.height\n    }\n}\n\nimpl Rectangle {\n    fn can_hold(\u0026self, other: \u0026Rectangle) -\u003e bool {\n        self.width \u003e other.width \u0026\u0026 self.height \u003e other.height\n    }\n}\n```\n\n## Summary\nStructs let you create custom types that are meaningful for your domain. By using structs, you can keep associated pieces of data connected to each other and name each piece to make your code clear. In impl blocks, you can define functions that are associated with your type, and methods are a kind of associated function that let you specify the behavior that instances of your structs have.\n\n\n# 6 Enums and Pattern Matching\nIn this chapter, we’ll look at `enumerations`, also referred to as `enums`. Enums allow you to define a type by enumerating its possible `variants`. \n\n### Defining an Enum\nWhere structs give you a way of grouping together related fields and data, like a `Rectangle` with its width and height, `enums` give you a way of saying a value is one of a `possible set of values`. For example, we may want to say that `Rectangle` is one of a set of possible shapes that also includes `Circle` and `Triangle`\n\n### Enum Values\nWe can express this concept in code by defining an IpAddrKind enumeration and listing the possible kinds an IP address can be, `V4` and `V6`.\n```rust\nenum IpAddrKind {\n    V4,\n    V6,\n}\n\nfn main() {\n    let four = IpAddrKind::V4; // We can create instances of each \n    let six = IpAddrKind::V6;  // of the two variants of `IpAddrKind`\n\n    route(IpAddrKind::V4); // we can call this function \n    route(IpAddrKind::V6); // with either variant: V4, V6\n}\n\nfn route(ip_kind: IpAddrKind) {} // for instance we can define a function that takes any IpAddrKind\n```\n\nRepresenting the same concept using just an enum is more concise: rather than an enum inside a struct, we can put data directly into each enum variant.\n```rust\nfn main() {\n    enum IpAddr {\n        V4(String),\n        V6(String),\n    }\n\n    let home = IpAddr::V4(String::from(\"127.0.0.1\")); // one liners to difine\n    let loopback = IpAddr::V6(String::from(\"::1\"));   // home and loopback\n}\n```\n\nThere’s another advantage to using an enum rather than a struct: `each variant can have different types and amounts of associated data`. Version four IP addresses will always have `four numeric components` that will have values between 0 and 255. If we wanted to store V4 addresses as four u8 values but still express V6 addresses as one String value, we `wouldn’t be able to with a struct`.\n```rust\n    enum IpAddr {\n        V4(u8, u8, u8, u8),\n        V6(String),\n    }\n\n    let home = IpAddr::V4(127, 0, 0, 1);\n\n    let loopback = IpAddr::V6(String::from(\"::1\"));\n```\n\nLet’s look at how the `standard library` defines `IpAddr`: it has the exact `enum` and `variants` that we’ve defined and used, but it embeds the address data inside the variants in the form of `two different structs`\n```rust\nstruct Ipv4Addr {\n    // --snip--\n}\n\nstruct Ipv6Addr {\n    // --snip--\n}\n\nenum IpAddr {\n    V4(Ipv4Addr),\n    V6(Ipv6Addr),\n}\n```\n\nLet’s look at another example of an enum: this one has a wide `variety of types` embedded in its variants.\n```rust\nenum Message {\n    Quit,\n    Move { x: i32, y: i32 },\n    Write(String),\n    ChangeColor(i32, i32, i32),\n}\n```\n\nThere is one more similarity between enums and structs: just as we’re able to define methods on structs using `impl`, we’re also able to define `methods` on enums. Here’s a method named `call` that we could define on our Message enum:\n```rust\nfn main() {\n    enum Message {\n        Quit,\n        Move { x: i32, y: i32 },\n        Write(String),\n        ChangeColor(i32, i32, i32),\n    }\n\n    impl Message {\n        fn call(\u0026self) {\n            // method body would be defined here\n        }\n    }\n\n    let m = Message::Write(String::from(\"hello\"));\n    m.call();\n}\n```\n\n### The Option Enum and Its Advantages Over Null Values\nThis section explores a case study of `Option`, which is another `enum` defined by the standard library. The Option type encodes the very common scenario in which a value could be `something` or it could be `nothing`.\nRust doesn’t have the `null` feature that many other languages have.\n```rust\nenum Option\u003cT\u003e {\n    None,\n    Some(T),\n}\n```\n\n`\u003cT\u003e` means that the `Some` variant of the `Option` enum can hold `one` piece of data of any type\n```rust\nlet some_number = Some(5);\nlet some_char = Some('e');\n\nlet absent_number: Option\u003ci32\u003e = None;\n```\n\n`Option\u003cT\u003e` and `T` (where T can be any type) are `different types`, the compiler won’t let us use an `Option\u003cT\u003e` value as if it were definitely a valid value\n```rust\nlet x: i8 = 5;\nlet y: Option\u003ci8\u003e = Some(5);\n\nlet sum = x + y;\n```\n\n## The match Control Flow Construct\nRust has an extremely powerful control flow construct called `match` that allows you to compare a value against a series of patterns and then execute code based on which pattern matches.\n\nFunction that takes an unknown US coin and, in a similar way as the counting machine, determines which coin it is and returns its value in cents\n```rust\nenum Coin {\n    Penny,\n    Nickel,\n    Dime,\n    Quarter,\n}\n\nfn value_in_cents(coin: Coin) -\u003e u8 {\n    match coin {\n        Coin::Penny =\u003e 1,\n        Coin::Nickel =\u003e 5,\n        Coin::Dime =\u003e 10,\n        Coin::Quarter =\u003e 25,\n    }\n}\n```\n\nIf you want to run `multiple lines` of code in a match arm, you must use curly brackets, and the comma following the arm is then optional\n```rust\nfn value_in_cents(coin: Coin) -\u003e u8 {\n    match coin {\n        Coin::Penny =\u003e {\n            println!(\"Lucky penny!\");\n            1\n        }\n        Coin::Nickel =\u003e 5,\n        Coin::Dime =\u003e 10,\n        Coin::Quarter =\u003e 25,\n    }\n}\n```\n\n### Patterns That Bind to Values\nAnother useful feature of `match` arms is that they can bind to the `parts of the values` that match the pattern. In the match expression for this code, we add a variable called `state` to the pattern that matches values of the variant `Coin::Quarter`\n```rust\n#[derive(Debug)]\nenum UsState {\n    Alabama,\n    Alaska,\n    // --snip--\n}\n\nenum Coin {\n    Penny,\n    Nickel,\n    Dime,\n    Quarter(UsState),\n}\n\nfn value_in_cents(coin: Coin) -\u003e u8 {\n    match coin {\n        Coin::Penny =\u003e 1,\n        Coin::Nickel =\u003e 5,\n        Coin::Dime =\u003e 10,\n        Coin::Quarter(state) =\u003e {\n            println!(\"State quarter from {:?}!\", state); //{:?} debug\n            25\n        }\n    }\n}\n\nfn main() {\n    value_in_cents(Coin::Quarter(UsState::Alaska));\n}\n```\n\n### Matching with Option\u003cT\u003e\nWe can also handle `Option\u003cT\u003e` using `match`\n```rust\n    fn plus_one(x: Option\u003ci32\u003e) -\u003e Option\u003ci32\u003e {\n        match x {\n            None =\u003e None,\n            Some(i) =\u003e Some(i + 1),\n        }\n    }\n\n    let five = Some(5);\n    let six = plus_one(five);\n    let none = plus_one(None);\n```\n\n### Matches Are Exhaustive\nThere’s one other aspect of match we need to discuss: the `arms patterns` must cover `all possibilities`. This will `NOT` work\n```rust\n    fn plus_one(x: Option\u003ci32\u003e) -\u003e Option\u003ci32\u003e {\n        match x {\n            Some(i) =\u003e Some(i + 1),\n        }\n    }\n```\n\n### Catch-all Patterns and the _ Placeholder\nUsing enums, we can also take special actions for a few particular values, but for `all other` values take one `default action`.\n```rust\n    let dice_roll = 9;\n    match dice_roll {\n        3 =\u003e add_fancy_hat(), // if 3 add fancy\n        7 =\u003e remove_fancy_hat(), // if 7 remove fancy\n        other =\u003e move_player(other), // default for all other \n    }\n\n    fn add_fancy_hat() {}\n    fn remove_fancy_hat() {}\n    fn move_player(num_spaces: u8) {}\n```\n\nLet’s change the rules of the game: now, if you roll `anything other than a 3 or a 7`, you must `roll again`. We no longer need to use the catch-all value, so we can change our code to use `_` instead of the variable named `other`\n```rust\n    let dice_roll = 9;\n    match dice_roll {\n        3 =\u003e add_fancy_hat(),\n        7 =\u003e remove_fancy_hat(),\n        _ =\u003e reroll(), // reroll if not 7 or 3\n    }\n\n    fn add_fancy_hat() {}\n    fn remove_fancy_hat() {}\n    fn reroll() {}\n```\n\nFinally, we’ll change the rules of the game one more time so that `nothing` else happens on your turn `if you roll anything` other than a 3 or a 7.\n```rust\n    let dice_roll = 9;\n    match dice_roll {\n        3 =\u003e add_fancy_hat(),\n        7 =\u003e remove_fancy_hat(),\n        _ =\u003e (), // do nothing if not 3 or 7\n    }\n\n    fn add_fancy_hat() {}\n    fn remove_fancy_hat() {}\n```\n\n### Concise Control Flow with if let\nThe `if let` syntax lets you combine if and let into a `less verbose` way to handle values that match `one` pattern while ignoring the rest.\n```rust\n    let config_max = Some(3u8);\n    match config_max {\n        Some(max) =\u003e println!(\"The maximum is configured to be {}\", max),\n        _ =\u003e (),\n    }\n```\n\n`Instead`, we could write this in a shorter way using `if let`.\n```rust\n    let config_max = Some(3u8);\n    if let Some(max) = config_max {\n        println!(\"The maximum is configured to be {}\", max);\n    }\n```\n\nIf we wanted to `count` all `non-quarter coins` we see while also announcing the state of the quarters, we could do that with a `match` expression, like this\n```rust\n    let mut count = 0;\n    match coin {\n        Coin::Quarter(state) =\u003e println!(\"State quarter from {:?}!\", state),\n        _ =\u003e count += 1,\n    }\n```\n\nOr we could use an `if let` and `else` expression\n```rust\n    let mut count = 0;\n    if let Coin::Quarter(state) = coin {\n        println!(\"State quarter from {:?}!\", state);\n    } else {\n        count += 1;\n    }\n```\n\n## Summary\nWe’ve now covered how to use enums to create custom types that can be one of a set of enumerated values. We’ve shown how the standard library’s `Option\u003cT\u003e` type helps you use the type system to prevent errors. When enum values have data inside them, you can use `match` or `if let` to extract and use those values, depending on how many cases you need to handle.\n\n# 7 Packages Crates and Modules\nRust has a number of `features` that allow you to `manage` your code’s organization, including which details are exposed, which details are private, and what names are in each scope in your programs. These features, sometimes collectively referred to as the `module system`, include:\n\n- `Packages`: A Cargo feature that lets you build, test, and share crates\n- `Crates`: A tree of modules that produces a library or executable\n- `Modules and use`: Let you control the organization, scope, and privacy of paths\n- `Paths`: A way of naming an item, such as a struct, function, or module\n\n### Packages and Crates\nA `crate` is the smallest amount of code that the Rust compiler `considers at a time`.\nA crate can come in one of two forms: a `binary crate` or a `library crate`.\n`Binary crates` are programs you can compile to an `executable` that you can run, such as a command-line program or a server - have function `main`\n`Library crates` don’t have `main` and define functionality intended to be shared with multiple projects\n```rust\n$ cargo new my-project\n     Created binary (application) `my-project` package\n$ ls my-project\nCargo.toml\nsrc\n$ ls my-project/src\nmain.rs\n```\n\n## Defining Modules to Control Scope and Privacy\n\n### Modules Cheat Sheet\n\n- `Start from the crate root`: When compiling a crate, the compiler first looks in the crate root file (usually `src/lib.rs` for a library crate or `src/main.rs` for a binary crate) for code to compile.\n\n- `Declaring modules`: In the crate root file, you can declare new modules; say, you declare a “garden” module with `mod garden;`. The compiler will look for the module’s code in these places:  \n-- Inline, within curly brackets that replace the semicolon following `mod garden`  \n-- In the file `src/garden.rs`  \n-- In the file `src/garden/mod.rs`  \n\n- `Declaring submodules`: In any file other than the crate root, you can declare submodules. For example, you might declare `mod vegetables;` in src/garden.rs. The compiler will look for the submodule’s code within the directory named for the parent module in these places:  \n-- Inline, directly following `mod vegetables`, within curly brackets instead of the semicolon  \n-- In the file `src/garden/vegetables.rs`  \n-- In the file `src/garden/vegetables/mod.rs`  \n\n- `Paths to code in modules`: Once a module is part of your crate, you can refer to code in that module from anywhere else in that same crate, as long as the privacy rules allow, using the path to the code. For example, an Asparagus type in the garden vegetables module would be found at `crate::garden::vegetables::Asparagus`.\n\n- `Private vs public`: Code within a module is private from its parent modules by default. To make a module public, declare it with `pub mod` instead of `mod`. To make items within a public module public as well, use pub before their declarations.\n\n- The `use` keyword: Within a scope, the use keyword creates shortcuts to items to reduce repetition of long paths. In any scope that can refer to `crate::garden::vegetables::Asparagus`, you can create a shortcut with use `crate::garden::vegetables::Asparagus;` and from then on you only need to write `Asparagus` to make use of that type in the scope.\n\nHere we create a binary crate named `backyard` that illustrates these rules. The crate’s directory, also named `backyard`, contains these files and directories:\n```rust\nbackyard\n├── Cargo.lock\n├── Cargo.toml\n└── src\n    ├── garden\n    │   └── vegetables.rs\n    ├── garden.rs\n    └── main.rs\n```\n\nThe crate root file in this case is `src/main.rs`, and it contains:\n```rust\nuse crate::garden::vegetables::Asparagus;\n\npub mod garden;\n\nfn main() {\n    let plant = Asparagus {};\n    println!(\"I'm growing {:?}!\", plant);\n}\n```\n\nThe `pub mod garden;` line tells the compiler to include the code it finds in `src/garden.rs`, which is:\n```rust\npub mod vegetables;\n```\nHere, `pub mod vegetables;` means the code in `src/garden/vegetables.rs` is included too. That code is:\n```rust\n#[derive(Debug)]\npub struct Asparagus {}\n```\n\n### Grouping Related Code in Modules\n`Modules` let us organize code within a crate for readability and easy reuse. Modules also allow us to control the `privacy` of items, because code within a module is `private by default`. \n\nIn the `restaurant industry`, some parts of a restaurant are referred to as `front of house` and others as `back of house`. Front of house is where customers are; this encompasses where the hosts seat customers, servers take orders and payment, and bartenders make drinks. Back of house is where the chefs and cooks work in the kitchen, dishwashers clean up, and managers do administrative work.\n\nCreate a `new library` named restaurant by running `cargo new restaurant --lib`.\nFilename: `src/lib.rs`:\n```rust\nmod front_of_house {\n    mod hosting {\n        fn add_to_waitlist() {}\n\n        fn seat_at_table() {}\n    }\n\n    mod serving {\n        fn take_order() {}\n\n        fn serve_order() {}\n\n        fn take_payment() {}\n    }\n}\n```\nWe define a module with the `mod keyword` followed by the name of the module (in this case, `front_of_house`).\n\n`src/main.rs` and `src/lib.rs` are called `crate roots`. The reason for their name is that the contents of either of these two files form a module named `crate` at the root of the crate’s module structure, known as the `module tree`.\n```rust\ncrate\n └── front_of_house\n     ├── hosting\n     │   ├── add_to_waitlist\n     │   └── seat_at_table\n     └── serving\n         ├── take_order\n         ├── serve_order\n         └── take_payment\n\n```\nThe module tree might remind you of the `filesystem’s directory tree` on your computer; this is a very `apt` comparison!\n\n### Paths for Referring to an Item in the Module Tree\nA path can take two forms:\n\n- An `absolute path` is the full path starting from a crate root; for code from an external crate, the absolute path begins with the crate name, and for code from the current crate, it starts with the literal crate.\n- A `relative path` starts from the current module and uses `self`, `super`, or an identifier in the current module.\n\u003e Our preference in general is to specify absolute paths because it’s more likely we’ll want to move code definitions and item calls independently of each other.\n\nBoth absolute and relative paths are followed by one or more identifiers separated by double colons `(::)`.\n```rust\nmod front_of_house {\n    mod hosting {\n        fn add_to_waitlist() {}\n    }\n}\n\npub fn eat_at_restaurant() {\n    // Absolute path\n    crate::front_of_house::hosting::add_to_waitlist();\n\n    // Relative path\n    front_of_house::hosting::add_to_waitlist();\n}\n```\n\u003e We have the correct `paths` for the hosting `module` and the `add_to_waitlist` function, but Rust won’t let us use them because it `doesn’t have access` to the private sections. \n\n### Exposing Paths with the pub Keyword\nWe want the `eat_at_restaurant` function in the parent module to have access to the `add_to_waitlist` function in the child module, so we mark the hosting module with the `pub` keyword\n```rust\nmod front_of_house {\n    pub mod hosting {\n        fn add_to_waitlist() {}\n    }\n}\n\npub fn eat_at_restaurant() {\n    // Absolute path\n    crate::front_of_house::hosting::add_to_waitlist();\n\n    // Relative path\n    front_of_house::hosting::add_to_waitlist();\n}\n```\n\u003e The `pub` keyword on a module only lets code in its `ancestor modules` refer to it, not access its `inner code`\n\nLet’s also make the `add_to_waitlist` function `public` by adding the `pub` keyword before its definition\n```rust\nmod front_of_house {\n    pub mod hosting {\n        pub fn add_to_waitlist() {}\n    }\n}\n\npub fn eat_at_restaurant() {\n    // Absolute path\n    crate::front_of_house::hosting::add_to_waitlist();\n\n    // Relative path\n    front_of_house::hosting::add_to_waitlist();\n}\n```\n\u003e The module tree should be defined in src/lib.rs. Then, any public items can be used in the binary crate by starting paths with the name of the package. The binary crate becomes a user of the library crate just like a completely external crate would use the library crate: it can only use the public API. This helps you design a good API; not only are you the author, you’re also a client!\n\n### Starting Relative Paths with super\nWe can construct relative paths that begin in the parent module, rather than the current module or the crate root, by using `super` at the start of the path.\n```rust\nfn deliver_order() {}\n\nmod back_of_house {\n    fn fix_incorrect_order() {\n        cook_order();\n        super::deliver_order();\n    }\n\n    fn cook_order() {}\n}\n```\n\n### Making Structs and Enums Public\nWe can also use `pub` to designate `structs` and `enums` as `public`, but there are a few details extra to the usage of pub with structs and enums. \nWe’ve defined a `public` `back_of_house::Breakfast` struct with a `public` `toast` field but a `private` `seasonal_fruit` field\n```rust\nmod back_of_house {\n    pub struct Breakfast {\n        pub toast: String,\n        seasonal_fruit: String,\n    }\n\n    impl Breakfast {\n        pub fn summer(toast: \u0026str) -\u003e Breakfast {\n            Breakfast {\n                toast: String::from(toast),\n                seasonal_fruit: String::from(\"peaches\"),\n            }\n        }\n    }\n}\n\npub fn eat_at_restaurant() {\n    // Order a breakfast in the summer with Rye toast\n    let mut meal = back_of_house::Breakfast::summer(\"Rye\");\n    // Change our mind about what bread we'd like\n    meal.toast = String::from(\"Wheat\");\n    println!(\"I'd like {} toast please\", meal.toast);\n\n    // The next line won't compile if we uncomment it; we're not allowed\n    // to see or modify the seasonal fruit that comes with the meal\n    // meal.seasonal_fruit = String::from(\"blueberries\");\n}\n```\n\nIn contrast, if we make an `enum` `public`, all of its variants are then `public`. We only need the `pub` before the enum keyword\n```rust\nmod back_of_house {\n    pub enum Appetizer {\n        Soup,\n        Salad,\n    }\n}\n\npub fn eat_at_restaurant() {\n    let order1 = back_of_house::Appetizer::Soup;\n    let order2 = back_of_house::Appetizer::Salad;\n}\n```\n\n### Bringing Paths into Scope with the use Keyword\nWe bring the `crate::front_of_house::hosting` module into the scope of the `eat_at_restaurant` function so we only have to specify `hosting::add_to_waitlist` to call the `add_to_waitlist` function in eat_at_restaurant\n** Note that use only creates the shortcut for the `particular scope` in which the `use` occurs.**\n```rust\nmod front_of_house {\n    pub mod hosting {\n        pub fn add_to_waitlist() {}\n    }\n}\n\nuse crate::front_of_house::hosting;\n\npub fn eat_at_restaurant() {\n    hosting::add_to_waitlist();\n}\n```\n\u003e Adding `use` and a `path` in a scope is similar to creating a `symbolic link` in the filesystem.\n\n### Creating Idiomatic use Paths\nSpecifying the `parent module` when calling the function makes it clear that the function isn’t `locally defined` while still minimizing repetition of the full path. \n\nOn the other hand, when bringing in `structs, enums, and other items` with `use`, it’s idiomatic to specify the `full path`.\n```rust\nuse std::collections::HashMap;\n\nfn main() {\n    let mut map = HashMap::new();\n    map.insert(1, 2);\n}\n```\n\u003e The exception to this idiom is if we’re bringing two items with the same name into scope with use statements, because Rust doesn’t allow that.\n\n### Providing New Names with the as Keyword\nThere’s another solution to the problem of bringing two types of the same name into the same scope with `use`: after the path, we can specify `as` and a new local name, or alias, for the type. \n```rust\nuse std::fmt::Result;\nuse std::io::Result as IoResult;\n\nfn function1() -\u003e Result {\n    // --snip--\n}\n\nfn function2() -\u003e IoResult\u003c()\u003e {\n    // --snip--\n}\n```\n\n### Re-exporting Names with pub use\nWe can combine `pub` and `use`. This technique is called `re-exporting` because we’re bringing an item into scope but also making that item available for others to bring into their scope.\n```rust\nmod front_of_house {\n    pub mod hosting {\n        pub fn add_to_waitlist() {}\n    }\n}\n\npub use crate::front_of_house::hosting;\n\npub fn eat_at_restaurant() {\n    hosting::add_to_waitlist();\n}\n```\n\n### Using External Packages\nTo bring `rand` definitions into the scope of our package, we added a use line starting with the name of the crate\n```rust\nuse rand::Rng;\n\nfn main() {\n    let secret_number = rand::thread_rng().gen_range(1..=100);\n}\n```\n\nwith `HashMap` we would use this line:\n```rust\nuse std::collections::HashMap;\n```\n\n### Using Nested Paths to Clean Up Large use Lists\nWe can use nested paths to bring items into scope `in one line`\n```rust\nuse std::{cmp::Ordering, io};\nuse std::io::{self, Write};\n```\n\n### The Glob Operator\nIf we want to bring `all` public items\n```rust\nuse std::collections::*;\n```\n\n## Separating Modules into Different Files\nWe’ll extract `modules` into `files` instead of having all the modules defined in the crate root file. \n\nFilename: src/lib.rs\n```rust\nmod front_of_house;\n\npub use crate::front_of_house::hosting;\n\npub fn eat_at_restaurant() {\n    hosting::add_to_waitlist();\n}\n```\n\nFilename: src/front_of_house.rs\n```rust\npub mod hosting;\n```\n\nFilename: src/front_of_house/hosting.rs\n```rust\npub fn add_to_waitlist() {}\n```\n\n## Summary\nRust lets you split a `package` into multiple `crates` and a crate into `modules` so you can refer to items defined in one module from another module. You can do this by specifying `absolute` or `relative` paths. These paths can be brought into scope with a `use` statement so you can use a shorter path for multiple uses of the item in that scope. Module code is `private by default`, but you can make definitions public by adding the `pub` keyword.\n\n\n# 8 Common Collections\nMost other data types represent one specific value, but collections can contain multiple values. Unlike the built-in array and tuple types, the data these collections point to is stored on the heap, which means the amount of data does not need to be known at compile time and can grow or shrink as the program runs.  \n- A `vector` allows you to store a variable number of values next to each other.\n- A `string` is a collection of characters. We’ve mentioned the String type previously, but in this chapter we’ll talk about it in depth.\n- A `hash map` allows you to associate a value with a particular key. It’s a particular implementation of the more general data structure called a map.\n\n## Storing Lists of Values with Vectors\nThe first collection type we’ll look at is `Vec\u003cT\u003e`, also known as a `vector`.\nTo create a new empty vector, we call the `Vec::new` function,\n```rust\n    let v: Vec\u003ci32\u003e = Vec::new();\n    let v = vec![1, 2, 3];\n```\n\n### Updating a Vector\nTo create a vector and then add elements to it, we can use the `push` method,\n```rust\n    let mut v = Vec::new();\n    v.push(5);\n    v.push(6);\n```\n\n### Reading Elements of Vectors\nThere are `two` ways `to reference` a value stored in a vector: via `indexing` or using the `get`\n```rust\n    let v = vec![1, 2, 3, 4, 5];\n\n    let third: \u0026i32 = \u0026v[2]; // using index\n    println!(\"The third element is {third}\");\n\n    let third: Option\u003c\u0026i32\u003e = v.get(2); // using get\n    match third {\n        Some(third) =\u003e println!(\"The third element is {third}\"),\n        None =\u003e println!(\"There is no third element.\"),\n    }\n```\n`Indexing` - this method is best used when you want your program to crash if there’s an attempt to access an element past the end of the vector.\nWhen the `get` method is passed an index that is outside the vector, it returns None `without panicking`.\n\n### Iterating over the Values in a Vector\nTo `access each element` in a vector in turn, we would iterate through all of the elements rather than use indices to access one at a time with `for loop`\n```rust\n    let v = vec![100, 32, 57];\n    for i in \u0026v {\n        println!(\"{i}\");\n    }\n```\n\nWe can also `iterate` over `mutable` references\n```rust\n    let mut v = vec![100, 32, 57];\n    for i in \u0026mut v {\n        *i += 50;\n    }\n\n```\n\n### Using an Enum to Store Multiple Types\nWhen we need `one type` to represent `elements of different types`, we can define and use an `enum`\n```rust\n    enum SpreadsheetCell {\n        Int(i32),\n        Float(f64),\n        Text(String),\n    }\n\n    let row = vec![\n        SpreadsheetCell::Int(3),\n        SpreadsheetCell::Text(String::from(\"blue\")),\n        SpreadsheetCell::Float(10.12),\n    ];\n```\n\n### Dropping a Vector Drops Its Elements\nLike any other struct, a vector is freed when it goes out of scope\n```rust\n    {\n        let v = vec![1, 2, 3, 4];\n\n        // do stuff with v\n    } // \u003c- v goes out of scope and is freed here\n```\n\n## Storing UTF-8 Encoded Text with Strings\nNew Rustaceans commonly get stuck on strings for a combination of three reasons: \n- Rust’s propensity for exposing possible errors  \n- strings being a more complicated data structure than many programmers give them credit for  \n- and UTF-8  \n\n### What Is a String?\nRust has only one string type in the core language, which is the string slice `str` that is usually seen in its borrowed form `\u0026str`\nThe `String` type, which is provided by Rust’s `standard library` rather than coded into the core language, is a `growable`, `mutable`, `owned`, `UTF-8` encoded string type. \n\n### Creating a New String\nMany of the `same operations` available with `Vec\u003cT\u003e` are available with `String` as well, because String is actually implemented as a `wrapper around a vector` of bytes with some extra guarantees, restrictions, and capabilities.\n```rust\n    let mut s = String::new();\n```\n\nOften, we’ll have some `initial data` that we want to start the string with. For that, we `use` the `to_string` method, which is available on any type that implements the `Display` trait\n```rust\n    let data = \"initial contents\";\n\n    let s = data.to_string();\n\n    // the method also works on a literal directly:\n    let s = \"initial contents\".to_string();\n```\n\nWe `can also` use the function `String::from` to create a String from a string literal.\n```rust\n    let s = String::from(\"initial contents\");\n```\n\u003e In this case, `String::from` and `to_string` do the `same` thing, so which you choose is a matter of style and readability.\n\n### Updating a String\nA String `can grow` in size and its contents can change, just like the contents of a `Vec\u003cT\u003e`, if you `push` more data into it. In addition, you can conveniently use the `+` operator or the `format!` macro to concatenate String values.\n\nWe can `grow` a String by using the `push_str` method to\n```rust\n    let mut s = String::from(\"foo\");\n    s.push_str(\"bar\");\n```\n\u003e The push_str method takes a string slice and `don’t take ownership` of the parameter\n\nThe `push` method takes a `single character` as a parameter and adds it to the String.\n```rust\n    let mut s = String::from(\"lo\");\n    s.push('l');\n```\n\nOften, you’ll want to `combine two` existing strings. One way to do so is to `use` the `+` operator\n```rust\n    let s1 = String::from(\"Hello, \");\n    let s2 = String::from(\"world!\");\n    let s3 = s1 + \u0026s2; // note s1 has been moved here and can no longer be used\n```\n\u003e The string s3 will contain Hello, world!. The reason `s1` is `no longer valid` after the addition, and the reason we used a `reference to s2`, has to do with the signature of the `method` that’s called when we use the + operator. The `+` operator `uses` the `add` method\n\nIf we need to concatenate multiple strings, the behavior of the + operator gets unwieldy. \nFor more `complicated string` combining, we can instead `use` the `format!` macro:\n```rust\n    let s1 = String::from(\"tic\");\n    let s2 = String::from(\"tac\");\n    let s3 = String::from(\"toe\");\n\n    let s = format!(\"{s1}-{s2}-{s3}\");\n```\n\n### Indexing into Strings\nRust strings `don’t support indexing`\nA `String` is a wrapper over a `Vec\u003cu8\u003e`.\nSometimes `UTF-8` stores as `1 byte`, sometimes with Unicode scalar value as `2 bytes`.\nTo avoid `returning an unexpected value` and causing `bugs` that might not be discovered immediately, Rust doesn’t compile this code at all and prevents misunderstandings early in the development process.\n\n### Bytes and Scalar Values and Grapheme Clusters! Oh My!\nAnother point about `UTF-8` is that there are actually `three` relevant `ways to look` at strings from Rust’s perspective: `as bytes`, `scalar values`, and `grapheme clusters`\n\u003e A final reason Rust `doesn’t allow us to index` into a String to get a character is that indexing operations are expected to always take constant time (O(1)). But it isn’t possible to guarantee that performance with a String, because `Rust would have to walk through the contents from the beginning to the index` to determine `how many valid` characters there were.\n\n### Slicing Strings\n`Indexing` into a string is `often a bad idea` because it’s `not clear` what the return type of the string-indexing `operation should be`: a byte value, a character, a grapheme cluster, or a string slice.\n\n### Methods for Iterating Over Strings\nThe `best way` to operate on pieces of strings is to be `explicit` about whether you want `characters or bytes`. For individual Unicode scalar values, use the `chars` method.\n```rust\nfor c in \"Зд\".chars() {\n    println!(\"{c}\");\n}\n```\nAlternatively, the `bytes` method returns each `raw byte`\n```rust\nfor b in \"Зд\".bytes() {\n    println!(\"{b}\");\n}\n```\n\n### Strings Are Not So Simple\nTo summarize, `strings are complicated`. Different programming languages make different choices about how to present this complexity to the programmer. Rust has chosen to make the `correct handling of String data the default` behavior for all Rust programs, which means programmers have to put more thought into `handling UTF-8` data upfront\n\n## Storing Keys with Associated Values in Hash Maps\nThe type `HashMap\u003cK, V\u003e` stores a mapping of `keys` of type K to `values` of type V using a hashing function, which determines how it places these keys and values into memory. \nHash maps are `useful` when you want to look up data `not by using an index`, as you can with vectors, but `by using a key` that can be of any type. \n\n### Creating a New Hash Map\nOne way to create an empty hash map is using new and adding elements with insert. Just like vectors, hash maps store their data on the heap. \n```rust\n    use std::collections::HashMap;\n    let mut scores = HashMap::new();\n    scores.insert(String::from(\"Blue\"), 10);\n    scores.insert(String::from(\"Yellow\"), 50);\n```\n\u003e we need to first `use the HashMap from the collections` portion of the standard library.\n\n### Accessing Values in a Hash Map\nWe `can get a value` out of the hash map by providing its key to the `get` method\n```rust\n    use std::collections::HashMap;\n\n    let mut scores = HashMap::new();\n\n    scores.insert(String::from(\"Blue\"), 10);\n    scores.insert(String::from(\"Yellow\"), 50);\n\n    let team_name = String::from(\"Blue\");\n    let score = scores.get(\u0026team_name).copied().unwrap_or(0);\n```\n\u003e Here, `score` will have the value that’s associated with the `Blue` team, and the result will be `10`. The `get` method returns an `Option\u003c\u0026V\u003e`; if there’s `no value` for that key in the hash map, get will return `None`. This program handles the `Option` by calling `copied` to get an `Option\u003ci32\u003e` rather than an `Option\u003c\u0026i32\u003e`, then `unwrap_or` to set score to zero if scores doesn't have an entry for the key.\n\nWe can `iterate` over each key/value pair in a `hash map` in a similar manner as we do with vectors, using a `for loop`\n```rust\n    use std::collections::HashMap;\n\n    let mut scores = HashMap::new();\n\n    scores.insert(String::from(\"Blue\"), 10);\n    scores.insert(String::from(\"Yellow\"), 50);\n\n    for (key, value) in \u0026scores {\n        println!(\"{key}: {value}\");\n    }\n```\n\n### Hash Maps and Ownership\nFor types that implement the `Copy trait, like i32`, the values are `copied into the hash` map. `For owned` values like `String`, the values will be `moved` and the hash map will be the `owner` of those values\n```rust\n    use std::collections::HashMap;\n\n    let field_name = String::from(\"Favorite color\");\n    let field_value = String::from(\"Blue\");\n\n    let mut map = HashMap::new();\n    map.insert(field_name, field_value);\n    // field_name and field_value are invalid at this point, try using them and\n    // see what compiler error you get!\n```\n\u003e We `aren’t able to use` the variables `field_name` and `field_value` after they’ve been moved into the hash map with the call to insert.\n\n### Updating a Hash Map\nWhen you want to change the data in a hash map, you have to decide how to handle the case when a key already has a value assigned.\n\nOverwriting a Value\n```rust\n    use std::collections::HashMap;\n\n    let mut scores = HashMap::new();\n\n    scores.insert(String::from(\"Blue\"), 10);\n    scores.insert(String::from(\"Blue\"), 25);\n\n    println!(\"{:?}\", scores);\n```\n\u003e If we insert a key and a value into a hash map and then insert that same key with a different value, the value associated with that key will be replaced\n\nAdding a Key and Value Only If a Key Isn’t Present\n```rust\n    use std::collections::HashMap;\n\n    let mut scores = HashMap::new();\n    scores.insert(String::from(\"Blue\"), 10);\n\n    scores.entry(String::from(\"Yellow\")).or_insert(50);\n    scores.entry(String::from(\"Blue\")).or_insert(50);\n\n    println!(\"{:?}\", scores);\n```\n\u003e if the key does exist in the hash map, the existing value should remain the way it is. If the key doesn’t exist, insert it and a value for it.\n\nUpdating a Value Based on the Old Value\n```rust\n    use std::collections::HashMap;\n\n    let text = \"hello world wonderful world\";\n\n    let mut map = HashMap::new();\n\n    for word in text.split_whitespace() {\n        let count = map.entry(word).or_insert(0);\n        *count += 1;\n    }\n\n    println!(\"{:?}\", map);\n```\n\u003e We use a hash map with the words as keys and increment the value to keep track of how many times we’ve seen that word\n\n### Hashing Functions\nBy default, HashMap uses a hashing function called `SipHash` \n\n# Error Handling\nRust groups errors into `two` major categories: `recoverable` and `unrecoverable errors`. For a recoverable error, such as a `file not found` error, we most likely just `want to report` the problem to the user and retry the operation. Unrecoverable errors are always symptoms of `bugs`, like `trying to access a location beyond the end of an array`, and so we want to immediately `stop` the program.\nRust `doesn’t have exceptions`. Instead, it has the type `Result\u003cT, E\u003e` for `recoverable` errors and the `panic!` macro that stops execution when the program encounters an `unrecoverable error`.\n\n## Unrecoverable Errors with panic!\nBy default, when a panic occurs, the program starts unwinding, which means Rust walks back up the stack and cleans up the data from each function it encounters. However, this walking back and cleanup is a lot of work. Rust, therefore, allows you to choose the alternative of immediately aborting, which ends the program without cleaning up.\n```\n//Cargo.toml file\n[profile.release]\npanic = 'abort'\n```\nSometimes, bad things happen in your code, and there’s nothing you can do about it. In these cases, Rust has the `panic!` macro\n```rust\nfn main() {\n    panic!(\"crash and burn\");\n}\n```\n\n### Using a panic! Backtrace\nWe can set the `RUST_BACKTRACE` environment variable to get a backtrace of exactly what happened to cause the error. A backtrace is a list of all the functions that `have been called to get to this point`.\n```sh\nRUST_BACKTRACE=1 cargo run\n```\n\u003e Debug symbols are `enabled by default` when using cargo build or cargo run without the `--release` flag, as we have here.\n\n### Recoverable Errors with Result\nMost errors aren’t serious enough to require the program to stop entirely.\n```rust\nenum Result\u003cT, E\u003e {\n    Ok(T),\n    Err(E),\n}\n```\n\nWe need to `add` to the code to take `different actions depending` on the `value` File::open `returns`\n```rust\nuse std::fs::File;\nfn main() {\n    let greeting_file_result = File::open(\"hello.txt\");\n    let greeting_file = match greeting_file_result {\n        Ok(file) =\u003e file, // return inner file\n        Err(error) =\u003e panic!(\"Problem opening the file: {:?}\", error), // panic\n    };\n}\n```\n\n### Matching on Different Errors\nWe want to take `different actions` for different failure reasons: `if File::open failed` because the file doesn’t exist, `we want to create` the file and return the handle to the new file\n```rust\nuse std::fs::File;\nuse std::io::ErrorKind;\n\nfn main() {\n    let greeting_file_result = File::open(\"hello.txt\");\n\n    let greeting_file = match greeting_file_result {\n        Ok(file) =\u003e file,\n        Err(error) =\u003e match error.kind() { // different kinds of errors\n            ErrorKind::NotFound =\u003e match File::create(\"hello.txt\") { // if not found try to create file\n                Ok(fc) =\u003e fc,\n                Err(e) =\u003e panic!(\"Problem creating the file: {:?}\", e), // panic if failed\n            },\n            other_error =\u003e {\n                panic!(\"Problem opening the file: {:?}\", other_error); // in other kind panic\n            }\n        },\n    };\n}\n```\n\nThe `match` expression is very useful but also very much a `primitive`. Here’s `another way` to write the same logic this time using `closures` and the `unwrap_or_else` method\n```rust\nuse std::fs::File;\nuse std::io::ErrorKind;\nfn main() {\n    let greeting_file = File::open(\"hello.txt\").unwrap_or_else(|error| {\n        if error.kind() == ErrorKind::NotFound {\n            File::create(\"hello.txt\").unwrap_or_else(|error| {\n                panic!(\"Problem creating the file: {:?}\", error);\n            })\n        } else {\n            panic!(\"Problem opening the file: {:?}\", error);\n        }\n    });\n}\n```\n\n### Shortcuts for Panic on Error: unwrap and expect\nIf the `Result` value is the `Ok` variant, `unwrap` will `return` the value inside the `Ok`. If the Result is the `Err` variant, unwrap will call the `panic!` macro for us.\n```rust\nuse std::fs::File;\nfn main() {\n    let greeting_file = File::open(\"hello.txt\").unwrap();\n}\n```\n\nSimilarly, the `expect` method lets us also `choose` the `panic!` error message. Using `expect instead of unwrap` and providing good error messages can convey your intent and `make tracking` down the source of a `panic easier`. \n```rust\nuse std::fs::File;\nfn main() {\n    let greeting_file = File::open(\"hello.txt\")\n        .expect(\"hello.txt should be included in this project\");\n}\n```\n\u003e In production-quality code, most Rustaceans choose `expect rather than unwrap`\n\n### Propagating Errors\nWhen a function’s implementation calls something `that might fail`, instead of handling the error within the function itself, you can `return the error` to the `calling code` so that it can decide what to do. This is known as `propagating`\n```rust\nuse std::fs::File;\nuse std::io::{self, Read};\nfn read_username_from_file() -\u003e Result\u003cString, io::Error\u003e {\n    let username_file_result = File::open(\"hello.txt\");\n    let mut username_file = match username_file_result {\n        Ok(file) =\u003e file,\n        Err(e) =\u003e return Err(e),\n    };\n    let mut username = String::new();\n    match username_file.read_to_string(\u0026mut username) {\n        Ok(_) =\u003e Ok(username), // return String if all ok\n        Err(e) =\u003e Err(e), // return Error if cant read\n    }\n}\n```\n\u003e It’s up to the calling code to decide what to do with those values. If the calling code gets an Err value, it could call panic! and crash the program, use a default username, or look up the username from somewhere other than a file, for example.\n\n### A Shortcut for Propagating Errors: the ? Operator\nThis pattern of `propagating` errors is so `common in Rust` that Rust provides the question mark operator `?` to make this easier.\n```rust\nfn read_username_from_file() -\u003e Result\u003cString, io::Error\u003e {\n    let mut username_file = File::open(\"hello.txt\")?;\n    let mut username = String::new();\n    username_file.read_to_string(\u0026mut username)?;\n    Ok(username)\n}\n```\n\u003e `error type` received is `converted` into the error type defined in the `return type` of the `current function` - function returns `one error type` to represent all the ways a function might fail\n\nThe `?` operator eliminates a lot of boilerplate and `makes` this function’s `implementation simpler`.\n```rust\nfn read_username_from_file() -\u003e Result\u003cString, io::Error\u003e {\n    let mut username = String::new();\n    File::open(\"hello.txt\")?.read_to_string(\u0026mut username)?;\n    Ok(username)\n}\n```\n\u003e If the value is an `Err`, the Err will be `returned` from the `whole function` as if we had used the `return` keyword so the error value gets propagated to the calling code.\n\n`Reading a file` into a string is a fairly `common operation`, so the standard library provides the convenient `fs::read_to_string`\n```rust\nfn read_username_from_file() -\u003e Result\u003cString, io::Error\u003e {\n    fs::read_to_string(\"hello.txt\")\n}\n```\n\n### Where The ? Operator Can Be Used\nThe `?` operator can only be `used` in functions whose `return` type is `compatible` with the value the ? is used on.\nThe `error message` also mentioned that ? `can be used` with `Option\u003cT\u003e` values as well.\n```rust\nfn last_char_of_first_line(text: \u0026str) -\u003e Option\u003cchar\u003e {\n    text.lines().next()?.chars().last()\n}\n```\n\u003e As with using ? on Result, you can only `use ?` on `Option` in a function that `returns an Option`\n\nLuckily, `main can also return a Result\u003c(), E\u003e`\n``` rust\nuse std::error::Error;\nuse std::fs::File;\nfn main() -\u003e Result\u003c(), Box\u003cdyn Error\u003e\u003e {\n    let greeting_file = File::open(\"hello.txt\")?;\n    Ok(())\n}\n```\n\u003e you can read `Box\u003cdyn Error\u003e` to mean `any kind of error`\n\nWhen a `main` function `returns` a `Result\u003c(), E\u003e`, the executable will exit with a value of `0` if main returns `Ok(())` and will exit with a `nonzero` value if main returns an `Err` value. \n\n## To panic! or Not to panic!\nYou could call `panic!` for `any error` situation, whether there’s a possible way to recover or not, but then you’re `making` the decision that a `situation` is `unrecoverable` on behalf of the calling code. When you choose to return a `Result` value, you `give` the calling code `options`. \n\n### Examples, Prototype Code, and Tests\nWhen you’re writing an `example` to illustrate some concept, also including robust `error-handling code` can make the example `less clear`. \nSimilarly, the `unwrap and expect` methods are very `handy` when `prototyping`, before you’re ready to decide how to handle errors.\nIf a method call fails in a `test`, you’d want the `whole test to fail`, even if that method isn’t the functionality under test.\n\n### Cases in Which You Have More Information Than the Compiler\nIf you can ensure by manually inspecting the code that you’ll `never have an Err variant`, it’s perfectly acceptable to call unwrap, and even `better to document the reason` you think you’ll never have an Err variant in the `expect` text\n```rust\n    let home: IpAddr = \"127.0.0.1\"\n        .parse()\n        .expect(\"Hardcoded IP address should be valid\");\n```\n\n### Guidelines for Error Handling\nIn cases where continuing could be `insecure or harmful`, the `best choice` might be to `call panic!` and alert the person using your library to the bug in their code so they can fix it during development.\nHowever, when `failure is expected`, it’s more appropriate to `return a Result` than to make a panic! call.\nWhen your code performs an operation that `could put a user at risk` if it’s called using `invalid values`, your code should `verify the values are valid first` and `panic` if the values aren’t valid. \n\u003e you can use `Rust’s type system` (and thus the type checking done by the compiler) to do `many of the checks` for you.\n\n### Creating Custom Types for Validation\nLet’s take the idea of using `Rust’s type system` to ensure we have a `valid value` one step further and look at creating a custom type for validation.\n`One way` to do this would be to parse the guess as an i32 instead of only a u32 to allow potentially negative numbers, and then `add a check everywhere` for the number being in range\n`Instead`, we can `make a new type` and put the validations in a function to create an instance of the type rather than repeating the validations everywhere.\n```rust\npub struct Guess { //define a struct that has a field named value that holds an i32\n    value: i32,\n}\nimpl Guess {\n    pub fn new(value: i32) -\u003e Guess { // creates instances of Guess values\n        if value \u003c 1 || value \u003e 100 { // check if value correct\n            panic!(\"Guess value must be between 1 and 100, got {}.\", value); // panic if not\n        }\n        Guess { value } // return if all ok\n    }\n    pub fn value(\u0026self) -\u003e i32 { // getter, because value is private\n        self.value\n    }\n}\n```\n\u003e A function that has a parameter or returns only numbers between 1 and 100 could then declare in its signature that it takes or returns a `Guess rather than an i32` and wouldn’t need to do any `additional checks` in its body.\n\n## Summary\nRust’s error handling features are designed to help you write more robust code. The panic! macro signals that your program is in a state it can’t handle and lets you tell the process to stop instead of trying to proceed with invalid or incorrect values. The Result enum uses Rust’s type system to indicate that operations might fail in a way that your code could recover from. You can use Result to tell code that calls your code that it needs to handle potential success or failure as well. Using panic! and Result in the appropriate situations will make your code more reliable in the face of inevitable problems.\n\n# Generic Types Traits Lifetimes\nEvery programming language has tools for effectively handling the duplication of concepts. In Rust, one such tool is `generics`: abstract stand-ins for concrete types or other properties. \n\n## Removing Duplication by Extracting a Function\nTo eliminate this duplication, we’ll create an `abstraction` by defining a `function` that operates on any list of integers passed in a parameter. \n```rust\nfn largest(list: \u0026[i32]) -\u003e \u0026i32 {\n    let mut largest = \u0026list[0];\n\n    for item in list {\n        if item \u003e largest {\n            largest = item;\n        }\n    }\n\n    largest\n}\n\nfn main() {\n    let number_list = vec![34, 50, 25, 100, 65];\n\n    let result = largest(\u0026number_list);\n    println!(\"The largest number is {}\", result);\n    assert_eq!(*result, 100);\n\n    let number_list = vec![102, 34, 6000, 89, 54, 2, 43, 8];\n\n    let result = largest(\u0026number_list);\n    println!(\"The largest number is {}\", result);\n    assert_eq!(*result, 6000);\n}\n```\n\nIn summary, here are the steps we took to change the code:\n- Identify duplicate code.  \n- Extract the duplicate code into the body of the function and specify the inputs and return values of that code in the function signature.  \n- Update the two instances of duplicated code to call the function instead.  \n\n## Generic Data Types\nWe use `generics` to create definitions for items `like function` signatures or structs, which we can then use with many different concrete data types. \n\n### In Function Definitions\nWhen we use a `parameter` in the body of the function, we have to `declare` the parameter name in the `signature` so the compiler knows what that name means.\n```rust\nfn largest\u003cT\u003e(list: \u0026[T]) -\u003e \u0026T {\n```\n\n### In Struct Definitions\nWe can also define `structs` to use a generic type parameter in one or more fields using the `\u003c\u003e` syntax.\n```rust\nstruct Point\u003cT\u003e {\n    x: T,\n    y: T,\n}\n\nfn main() {\n    let integer = Point { x: 5, y: 10 };\n    let float = Point { x: 1.0, y: 4.0 };\n}\n```\n\u003e Note that because we’ve used only `one generic` type to define `Point\u003cT\u003e`, this definition says that the Point\u003cT\u003e struct is generic over `some type T`, and the fields x and y are `both that same type`, whatever that type may be.\n\nTo define a Point struct where x and y are both `generics` but could have `different types`, we can use `multiple generic type` parameters. \n```rust\nstruct Point\u003cT, U\u003e {\n    x: T,\n    y: U,\n}\n\nfn main() {\n    let both_integer = Point { x: 5, y: 10 };\n    let both_float = Point { x: 1.0, y: 4.0 };\n    let integer_and_float = Point { x: 5, y: 4.0 };\n}\n```\n\n### In Enum Definitions\nWe can define enums to hold `generic data` types in their variants.\n```rust\nenum Option\u003cT\u003e {\n    Some(T),\n    None,\n}\n```\n\nEnums can use `multiple generic` types as well. \n```rust\nenum Result\u003cT, E\u003e {\n    Ok(T),\n    Err(E),\n}\n```\n\n### In Method Definitions\nWe can implement methods on structs and enums and use `generic types` in their `definitions`, too.\n```rust\nstruct Point\u003cT\u003e {\n    x: T,\n    y: T,\n}\n\nimpl\u003cT\u003e Point\u003cT\u003e { // using generic data type \u003cT\u003e\n    fn x(\u0026self) -\u003e \u0026T {\n        \u0026self.x\n    }\n}\n\nfn main() {\n    let p = Point { x: 5, y: 10 };\n\n    println!(\"p.x = {}\", p.x());\n}\n```\n\nGeneric type parameters in a struct definition `aren’t always the same` as those you use in that `same struct’s method` signatures.\n```rust\nstruct Point\u003cX1, Y1\u003e {\n    x: X1,\n    y: Y1,\n}\n\nimpl\u003cX1, Y1\u003e Point\u003cX1, Y1\u003e {\n    fn mixup\u003cX2, Y2\u003e(self, other: Point\u003cX2, Y2\u003e) -\u003e Point\u003cX1, Y2\u003e {\n        Point {\n            x: self.x,\n            y: other.y,\n        }\n    }\n}\n\nfn main() {\n    let p1 = Point { x: 5, y: 10.4 };\n    let p2 = Point { x: \"Hello\", y: 'c' };\n\n    let p3 = p1.mixup(p2);\n\n    println!(\"p3.x = {}, p3.y = {}\", p3.x, p3.y);\n}\n```\n\u003e In main, we’ve defined a Point that has an i32 for x (with value 5) and an f64 for y (with value 10.4). The p2 variable is a Point struct that has a string slice for x (with value \"Hello\") and a char for y (with value c). Calling mixup on p1 with the argument p2 gives us p3, which will have an i32 for x, because x came from p1. The p3 variable will have a char for y, because y came from p2. The println! macro call will print p3.x = 5, p3.y = c.\n\n### Performance of Code Using Generics\nRust accomplishes this by performing `monomorphization` of the code using generics at compile time. Monomorphization is the process of `turning generic code` into specific code by `filling` in the `concrete types` that are used when compiled. \n\n## Traits: Defining Shared Behavior\nA `trait defines functionality` a particular type has and can share `with other types`.\n\n### Defining a Trait \nA type’s behavior consists of the `methods` we can call on that `type`. `Different types` share the `same behavior` if we can call the `same methods` on all of those types. `Trait` definitions are a way to `group method` signatures together to define a set of behaviors necessary `to accomplish some purpose`.\n\nWe want to make a media `aggregator library crate` named aggregator that can `display summaries` of data that might be stored in a NewsArticle or Tweet instance. To do this, we need a `summary from each type`, and we’ll request that summary by calling a `summarize method` on an instance. \n```rust\npub trait Summary {\n    fn summarize(\u0026self) -\u003e String;\n}\n```\n\n### Implementing a Trait on a Type\nNow that we’ve defined the desired signatures of the `Summary trait’s methods`, we can implement it on the types in our media aggregator.\n```rust\npub trait Summary {\n    fn summarize(\u0026self) -\u003e String;\n}\n\npub struct NewsArticle {\n    pub headline: String,\n    pub location: String,\n    pub author: String,\n    pub content: String,\n}\n\nimpl Summary for NewsArticle { // trait Summary for NewsArticle\n    fn summarize(\u0026self) -\u003e String {\n        format!(\"{}, by {} ({})\", self.headline, self.author, self.location)\n    }\n}\n\npub struct Tweet {\n    pub username: String,\n    pub content: String,\n    pub reply: bool,\n    pub retweet: bool,\n}\n\nimpl Summary for Tweet { // trait Summary for Tweet\n    fn summarize(\u0026self) -\u003e String {\n        format!(\"{}: {}\", self.username, self.content)\n    }\n}\n```\n\u003e Implementing a trait on a type is similar to implementing regular methods. The difference is that after impl, we put the trait name we want to implement, then use the for keyword, and then specify the name of the type we want to implement the trait for.\n\nNow `call the trait` methods on instances of NewsArticle and Tweet in the same way we call `regular methods`.\n```rust\nuse aggregator::{Summary, Tweet};\n\nfn main() {\n    let tweet = Tweet {\n        username: String::from(\"horse_ebooks\"),\n        content: String::from(\n            \"of course, as you probably already know, people\",\n        ),\n        reply: false,\n        retweet: false,\n    };\n\n    println!(\"1 new tweet: {}\", tweet.summarize());\n}\n```\n\u003e But we `can’t implement external traits on external types`. For example, we can’t implement the Display trait on Vec\u003cT\u003e within our aggregator crate, because Display and Vec\u003cT\u003e are both defined in the standard library and aren’t local to our aggregator crate. This restriction is part of a property called `coherence`, and more specifically the `orphan rule`, so named because the parent type is not present. This rule ensures that `other people’s code can’t break your code` and vice versa. Without the rule, two crates could implement the same trait for the same type, and Rust wouldn’t know which implementation to use.\n\n### Default Implementations\nSometimes it’s useful to have `default behavior for some or all of the methods` in a trait instead of requiring implementations for all methods on every type. \n```rust\npub trait Summary {\n    fn summarize(\u0026self) -\u003e String {\n        String::from(\"(Read more...)\")\n    }\n}\nimpl Summary for NewsArticle {}\n```\n\nDefault implementations can call other methods in the same trait, even if those other methods don’t have a default implementation.\n```rust\npub trait Summary { // trait with 2 methods\n    fn summarize_author(\u0026self) -\u003e String;\n\n    fn summarize(\u0026self) -\u003e String {\n        format!(\"(Read more from {}...)\", self.summarize_author())\n    }\n}\nimpl Summary for Tweet { // define only summarize_author()\n    fn summarize_author(\u0026self) -\u003e String {\n        format!(\"@{}\", self.username)\n    }\n}\n// can use in main default trait summarize()\nprintln!(\"1 new tweet: {}\", tweet.summarize());\n```\n\n### Traits as Parameters\nNow that you know `how to define and implement traits`, we can explore how to use traits to `define functions` that accept `many different types`. To do this, we use the impl Trait syntax.\n```rust\npub fn notify(item: \u0026impl Summary) {\n    println!(\"Breaking news! {}\", item.summarize());\n}\n```\n\u003e Instead of a concrete type for the item parameter, we specify the impl keyword and the trait name.\n\n### Trait Bound Syntax\nThe `impl Trait syntax` works for straightforward cases but is actually `syntax sugar` for a longer form known as a `trait bound`;\n```rust\npub fn notify\u003cT: Summary\u003e(item: \u0026T) {\n    println!(\"Breaking news! {}\", item.summarize());\n}\n```\n\u003e Using `impl Trait` is appropriate `if we want` this function to allow item1 and item2 to have `different types`\n\n### Specifying Multiple Trait Bounds with the + Syntax\nSay we wanted notify to use display formatting as well as summarize on item: we specify in the notify definition that item must implement `both Display and Summary`\n```rust\npub fn notify(item: \u0026(impl Summary + Display)) {\n// or generic\npub fn notify\u003cT: Summary + Display\u003e(item: \u0026T) {\n```\n\n### Clearer Trait Bounds with where Clauses\nEach generic has its own trait bounds, so functions with multiple generic type parameters can contain `lots of trait bound` information between the function’s name and its parameter list. specifying trait bounds inside a `where clause`\n```rust\nfn some_function\u003cT: Display + Clone, U: Clone + Debug\u003e(t: \u0026T, u: \u0026U) -\u003e i32 {\n// with where\nfn some_function\u003cT, U\u003e(t: \u0026T, u: \u0026U) -\u003e i32\nwhere\n    T: Display + Clone,\n    U: Clone + Debug,\n{\n```\n\n### Returning Types that Implement Traits\nWe can also `use the impl Trait syntax in the return position` to return a value of some type that implements a `trait`\n```rust\nfn returns_summarizable() -\u003e impl Summary {\n    Tweet {\n        username: String::from(\"horse_ebooks\"),\n        content: String::from(\n            \"of course, as you probably already know, people\",\n        ),\n        reply: false,\n        retweet: false,\n    }\n}\n```\n\u003e By using impl Summary for the return type, we specify that the `returns_summarizable` function returns some type that implements the `Summary trait` without naming the concrete type. you can only use impl Trait if you’re returning a `single type`.\n\n### Using Trait Bounds to Conditionally Implement Methods\nBy using a trait bound with an impl block that uses generic type parameters, we can implement methods conditionally for types that implement the specified traits.\n```rust\nuse std::fmt::Display;\n\nstruct Pair\u003cT\u003e {\n    x: T,\n    y: T,\n}\n\nimpl\u003cT\u003e Pair\u003cT\u003e { // always implements the new function to return a new instance of Pair\u003cT\u003e\n    fn new(x: T, y: T) -\u003e Self {\n        Self { x, y }\n    }\n}\n\nimpl\u003cT: Display + PartialOrd\u003e Pair\u003cT\u003e { // implements the cmp_display method only if its inner type T implements the PartialOrd and Display\n    fn cmp_display(\u0026self) {\n        if self.x \u003e= self.y {\n            println!(\"The largest member is x = {}\", self.x);\n        } else {\n            println!(\"The largest member is y = {}\", self.y);\n        }\n    }\n}\n```\n\u003e Implementations of a trait on any type that `satisfies the trait bounds` are called `blanket implementations` and are extensively used in the Rust standard library. \n\nFor example, the standard library implements the ToString trait on any type that implements the Display trait. \n```rust\nimpl\u003cT: Display\u003e ToString for T {\n    // --snip--\n}\n```\n\n## Validating References with Lifetimes\nRather than ensuring that a type has the behavior we want, `lifetimes ensure` that references are `valid as long as we need` them to be.\n\n### Preventing Dangling References with Lifetimes\nThe main aim of lifetimes is to prevent `dangling references`, which cause a program to `reference data other` than the `data it’s intended to reference`.\n```rust\nfn main() {\n    let r;\n    {\n        let x = 5;\n        r = \u0026x; // asign r to \u0026x\n    }\n    println!(\"r: {}\", r); // x is no longer valid - out of scope\n}\n```\n\n### The Borrow Checker\nThe Rust compiler has a `borrow checker` that `compares` scopes to determine whether `all borrows are valid`.\n```rust\nfn main() {\n    let r;                // ---------+-- 'a\n                          //          |\n    {                     //          |\n        let x = 5;        // -+-- 'b  |\n        r = \u0026x;           //  |       |\n    }                     // -+       |\n                          //          |\n    println!(\"r: {}\", r); //          |\n}                         // ---------+\n``` \n\u003e Here, we’ve annotated the lifetime of `r` with `'a` and the lifetime of `x` with `'b`. As you can see, the inner `'b` block is much smaller than the outer `'a` lifetime block\n\nFixes the code so it `doesn’t have a dangling reference`\n```rust\nfn main() {\n    let x = 5;            // ----------+-- 'b\n                          //           |\n    let r = \u0026x;           // --+-- 'a  |\n                          //   |       |\n    println!(\"r: {}\", r); //   |       |\n                          // --+       |\n}                         // ----------+\n```\n\u003e Here, `x` has the lifetime `'b`, which in this case is larger than `'a`\n\n### Generic Lifetimes in Functions\nWe’ll write a function that returns the longer of two string slices. \n```rust\nfn main() {\n    let string1 = String::from(\"abcd\");\n    let string2 = \"xyz\";\n\n    let result = longest(string1.as_str(), string2);\n    println!(\"The longest string is {}\", result);\n}\n```\n\u003e Note that we want the function to take string slices, which are references, rather than strings, because we don’t want the longest function to take ownership of its parameters.\n\nIf we try to implement the longest function, it won’t compile.\n```rust\nfn longest(x: \u0026str, y: \u0026str) -\u003e \u0026str {\n    if x.len() \u003e y.len() {\n        x\n    } else {\n        y\n    }\n}\n```\n\u003e To `fix` this error, we’ll `add generic lifetime parameters` that define the relationship between the references so the borrow checker can perform its analysis.\n\n### Lifetime Annotation Syntax\nLifetime annotations `don’t change how long any of the references live`. Rather, they `describe the relationships of the lifetimes` of multiple references to each other without affecting the lifetimes.\n```rust\n\u0026i32        // a reference\n\u0026'a i32     // a reference with an explicit lifetime\n\u0026'a mut i32 // a mutable reference with an explicit lifetime\n```\n\n### Lifetime Annotations in Function Signatures\nDeclare the `generic lifetime parameters` inside `angle brackets` between the function name and the parameter list, just as we did with `generic type parameters`.\n```rust\nfn longest\u003c'a\u003e(x: \u0026'a str, y: \u0026'a str) -\u003e \u0026'a str {\n    if x.len() \u003e y.len() {\n        x\n    } else {\n        y\n    }\n}\n```\n\n### Lifetime Annotations in Struct Definitions\nSo far, the structs we’ve defined `all hold owned types`. We can define `structs to hold references`, but in that case we would `need to add a lifetime annotation` on every reference in the struct’s definition. \n```rust\nstruct ImportantExcerpt\u003c'a\u003e {\n    part: \u0026'a str,\n}\n```\n\n### Lifetime Elision\nLifetimes on function or method parameters are called `input lifetimes`, and lifetimes on return values are called `output lifetimes`.\nThe `first rule` is that the compiler assigns a `lifetime parameter to each parameter` that’s a reference. `fn foo\u003c'a\u003e(x: \u0026'a i32);`\nThe `second rule` is that, if there is `exactly one input` lifetime parameter, that lifetime is assigned to `all output lifetime` parameters: `fn foo\u003c'a\u003e(x: \u0026'a i32) -\u003e \u0026'a i32`\nThe `third rule` is that, if there are multiple input lifetime parameters, but one of them is `\u0026self or \u0026mut self` because this is a method, the lifetime of self is assigned to `all output lifetime` parameters. \n\n### Lifetime Annotations in Method Definitions\nWhen we `implement methods` on a struct with lifetimes, we `use` the `same syntax as that of generic type parameters` shown\n```rust\n//no lifetime\nimpl\u003c'a\u003e ImportantExcerpt\u003c'a\u003e {\n    fn level(\u0026self) -\u003e i32 {\n        3\n    }\n}\n\n//third lifetime elision rule\nimpl\u003c'a\u003e ImportantExcerpt\u003c'a\u003e {\n    fn announce_and_return_part(\u0026self, announcement: \u0026str) -\u003e \u0026str {\n        println!(\"Attention please: {}\", announcement);\n        self.part\n    }\n}\n```\n\n### The Static Lifetime\n`'static`, which denotes that the affected `reference` can `live` for the `entire duration of the program`. All `string` literals have the `'static` lifetime, which we can annotate as follows:\n```rust\nlet s: \u0026'static str = \"I have a static lifetime.\";\n```\n\n### Generic Type Parameters, Trait Bounds, and Lifetimes Together\nLet’s briefly look at the syntax of specifying generic type parameters, trait bounds, and lifetimes `all in one` function!\n```rust\nuse std::fmt::Display;\n\nfn longest_with_an_announcement\u003c'a, T\u003e(\n    x: \u0026'a str,\n    y: \u0026'a str,\n    ann: T,\n) -\u003e \u0026'a str\nwhere\n    T: Display,\n{\n    println!(\"Announcement! {}\", ann);\n    if x.len() \u003e y.len() {\n        x\n    } else {\n        y\n    }\n}\n```\n\u003eThis is the longest function from Listing 10-21 that returns the longer of two string slices. But now it has an extra parameter named ann of the generic type T, which can be filled in by any type that implements the Display trait as specified by the where clause. This extra parameter will be printed using {}, which is why the Display trait bound is necessary. Because lifetimes are a type of generic, the declarations of the lifetime parameter 'a and the generic type parameter T go in the same list inside the angle brackets after the function name.\n\n# 11 How to Write Tests\nIn his 1972 essay “The Humble Programmer,” Edsger W. Dijkstra said that “Program testing can be a very effective way to show the presence of bugs, but it is hopelessly inadequate for showing their absence.”\n\n## How to Write Tests\n3 actions\n- Set up any needed data or state.  \n- Run the code you want to test.  \n- Assert the results are what you expect.  \n\n### The Anatomy of a Test Function\nExample; `cargo test` to run test\n```rust\n#[cfg(test)]\nmod tests {\n    #[test] // this attribute indicates this is a test function\n    fn it_works() {\n        let result = 2 + 2;\n        assert_eq!(result, 4); //macro to assert that result, which contains the result of adding 2 and 2, equals 4\n    }\n}\n```\n\n### Checking Results with the assert! Macro\nThe `assert!` macro, provided by the standard library, is useful when you want to ensure that some condition in a test `evaluates to true`\n```rust\n#[derive(Debug)]\nstruct Rectangle {\n    width: u32,\n    height: u32,\n}\n\nimpl Rectangle {\n    fn can_hold(\u0026self, other: \u0026Rectangle) -\u003e bool {\n        self.width \u003e other.width \u0026\u0026 self.height \u003e other.height\n    }\n}\n\n#[cfg(test)]\nmod tests {\n    use super::*; // anything we define in the outer module is available to this tests module.\n\n    #[test]\n    fn larger_can_hold_smaller() {\n        let larger = Rectangle {\n            width: 8,\n            height: 7,\n        };\n        let smaller = Rectangle {\n            width: 5,\n            height: 1,\n        };\n\n        assert!(larger.can_hold(\u0026smaller));\n    }\n\n    #[test]\n    fn smaller_cannot_hold_larger() {\n        let larger = Rectangle {\n            width: 8,\n            height: 7,\n        };\n        let smaller = Rectangle {\n            width: 5,\n            height: 1,\n        };\n\n        assert!(!smaller.can_hold(\u0026larger));\n    }    \n}\n```\n\n### Testing Equality with the assert_eq! and assert_ne! Macros\nThese macros compare two arguments for `equality or inequality`, respectively. They’ll `also print the two values` if the `assertion fails`, which makes it easier to see why the test failed; \n```rust\npub fn add_two(a: i32) -\u003e i32 {\n    a + 2\n}\n\n#[cfg(test)]\nmod tests {\n    use super::*;\n\n    #[test]\n    fn it_adds_two() {\n        assert_eq!(4, add_two(2));\n    }\n}\n```\n\n### Adding Custom Failure Messages\nAny arguments specified `after the required arguments` are passed along to the `format!` macro\n```rust\n    #[test]\n    fn greeting_contains_name() {\n        let result = greeting(\"Carol\");\n        assert!(\n            result.contains(\"Carol\"),\n            \"Greeting did not contain name, value was `{}`\",\n            result\n        );\n    }\n```\n\n### Checking for Panics with should_panic\nIn addition to checking return values, it’s important to check that our code handles error conditions as we expect. \n```rust\npub struct Guess {\n    value: i32,\n}\n\nimpl Guess {\n    pub fn new(value: i32) -\u003e Guess {\n        if value \u003c 1 || value \u003e 100 {\n            panic!(\"Guess value must be between 1 and 100, got {}.\", value);\n        }\n\n        Guess { value }\n    }\n}\n\n#[cfg(test)]\nmod tests {\n    use super::*;\n\n    #[test]\n    // The test passes if the code inside the function panics\n    #[should_panic(expected = \"less than or equal to 100\")]\n    fn greater_than_100() {\n        Guess::new(200);\n    }\n}\n```\n\n### Using Result\u003cT, E\u003e in Tests\nUse `Result\u003cT, E\u003e` and return an `Err` instead of `panicking`\n```rust\n#[cfg(test)]\nmod tests {\n    #[test]\n    fn it_works() -\u003e Result\u003c(), String\u003e {\n        if 2 + 2 == 4 {\n            Ok(())\n        } else {\n            Err(String::from(\"two plus two does not equal four\"))\n        }\n    }\n}\n```\n\n## Controlling How Tests Are Run\n`Some` command line `options go` to `cargo test`, and some go `to the resulting test binary`. `To separate` these two types of arguments, you list the arguments that go to `cargo test` followed by the separator `--` and then the ones that go to the test binary. \n\n### Running Tests in Parallel or Consecutively\nWhen you run multiple tests, `by default` they run `in parallel` using threads, meaning they finish running faster and you get feedback quicker. \n```sh\ncargo test -- --test-threads=1\n```\n\n### Showing Function Output\n`By default`, if a test passes, Rust’s test library `captures anything` printed to standard output. To show `println!` use\n```sh\ncargo test -- --show-output\n```\n\n### Running a Subset of Tests by Name\nRunning Single Tests\n```sh\ncargo test one_hundred\n```\n\nFiltering to Run Multiple Tests. Two of our tests’ names `contain add`, we can run those two by running:\n```sh\ncargo test add\n```\n\nIgnoring Some Tests Unless Specifically Requested\n```rust\n#[test]\n#[ignore]\nfn expensive_test() {\n    // code that takes an hour to run\n}\n```\n\n## Test Organization\nThe Rust community thinks about tests in terms of `two main categories`: `unit tests` and `integration tests`. `Unit tests` are `small` and more focused, `testing one module` in isolation at a time, and can test `private interfaces`. `Integration tests` are entirely `external` to your library and use your code in the same way any other external code would, using only `the public interface` and potentially exercising `multiple modules per test`.\n\n### Unit Tests\nYou’ll put unit tests in the src directory in each file with the code that they’re testing. The convention is to create a module named tests in each file to contain the test functions and to annotate the module with cfg(test).\n\nThe Tests Module and #[cfg(test)]\n```rust\n#[cfg(test)]\nmod tests { // create module tests\n    #[test]\n    fn it_works() {\n        let result = 2 + 2;\n        assert_eq!(result, 4);\n    }\n}\n```\n\nTesting Private Functions\n```rust\npub fn add_two(a: i32) -\u003e i32 {\n    internal_adder(a, 2)\n}\n\nfn internal_adder(a: i32, b: i32) -\u003e i32 { // without pub\n    a + b\n}\n\n#[cfg(test)]\nmod tests {\n    use super::*; // bring all fn to scope \n\n    #[test]\n    fn internal() {\n        assert_eq!(4, internal_adder(2, 2));\n    }\n}\n```\n\u003eThere’s debate within the testing community about whether or not private functions should be tested directly\n\n### Integration Tests\nIn Rust, integration tests are entirely external to your library.They use your library in the same way any other code would, which means they can only call functions that are part of your library’s public API.\n\nThe tests Directory\n```sh\nadder\n├── Cargo.lock\n├── Cargo.toml\n├── src\n│   └── lib.rs\n└── tests\n    └── integration_test.rs\n```\n```rust\nuse adder; // bring lib to tests\n#[test]\nfn it_adds_two() {\n    assert_eq!(4, adder::add_two(2));\n}\n```\n\u003e We don’t need to annotate any code in `tests/integration_test.rs` with `#[cfg(test)]`\n\nIntegration Tests for Binary Crates\n\u003eIf our project is a binary crate that only contains a src/main.rs file and doesn’t have a src/lib.rs file, we `can’t create integration tests` in the tests directory and bring functions defined in the src/main.rs file into scope with a use statement. `Only library crates expose functions` that other crates can use; binary crates are meant to be run on their own.\n\n# Building a Command Line Program\nOur `grep` project will combine a number of concepts you’ve learned so far:\n- Organizing code (using what you learned about modules in Chapter 7)  \n- Using vectors and strings (collections, Chapter 8)  \n- Handling errors (Chapter 9)  \n- Using traits and lifetimes where appropriate (Chapter 10)  \n- Writing tests (Chapter 11)  \n\n## Accepting Command Line Arguments\n```sh\ncargo new minigrep\ncd minigrep\ncargo run -- searchstring example-filename.txt\n```\n\u003eTwo hyphens to indicate the following arguments are for our program rather than for cargo, a string to search for, and a path to a file to search in\n\n### Reading the Argument Values\nThe code in allows your minigrep program to read any command line arguments passed to it and then collect the values into a vector.\n```rust\nuse std::env;\n\nfn main() {\n    let args: Vec\u003cString\u003e = env::args().collect();\n    dbg!(args);\n}\n```\n\n### Saving the Argument Values in Variables\nNow we need to save the values of the `two arguments` in `variables` so we can use the values throughout the rest of the program.\n```rust\nuse std::env;\n\nfn main() {\n    let args: Vec\u003cString\u003e = env::args().collect();\n\n    let query = \u0026args[1];\n    let file_path = \u0026args[2];\n\n    println!(\"Searching for {}\", query);\n    println!(\"In file {}\", file_path);\n}\n```\n\n### Reading a File\nWith the text in place, edit src/main.rs and add code to read the file\n```rust\nuse std::env;\nuse std::fs;\n\nfn main() {\n    // --snip--\n    println!(\"In file {}\", file_path);\n\n    let contents = fs::read_to_string(file_path)\n        .expect(\"Should have been able to read the file\");\n\n    println!(\"With text:\\n{contents}\");\n}\n```\n\u003eThe code read and then printed the contents of the file. But the code has a `few flaws`. At the moment, the `main` function has `multiple responsibilities`: generally, functions are clearer and easier to maintain if each function is responsible for `only one idea`. The other problem is that we’re `not handling errors` as well as we could.\n\n## Refactoring to Improve Modularity and Error Handling\nTo improve our program, we’ll fix `four problems`\n- our main function now performs `two tasks`  \n- best to `group` the `configuration variables` into one structure to make their purpose clear  \n- reading a file can fail in a `number of ways`  \n- it would be best if all the `error-handling` code `were in one place` so future maintainers had only one place to consult the code\n\n### Separation of Concerns for Binary Projects\nRust community has developed `guidelines` for splitting the separate concerns:\n- Split your program into a `main.rs` and a `lib.rs` and move your program’s logic to lib.rs.  \n- As long as your command `line parsing logic is small`, it can remain `in main.rs`.  \n- When the command line `parsing logic starts getting complicated`, extract it from main.rs and move it to `lib.rs`.  \n\nThe `responsibilities` that remain in the `main function` after this process should be limited to the following:\n- `Calling` the command line `parsing logic` with the argument values  \n- `Setting up` any other `configuration`  \n- `Calling a run` function in lib.rs  \n- `Handling the error` if run returns an error  \n\n\u003eBecause you `can’t test the main` function directly, this structure lets you test all of your program’s logic by moving it into functions in lib.rs. The code that remains in `main.rs will be small` enough to `verify` its correctness `by reading it`.\n\n### Extracting the Argument Parser\nPrepare for moving the command line `parsing logic to src/lib.rs`\n```rust\nfn main() {\n    let args: Vec\u003cString\u003e = env::args().collect();\n    let (query, file_path) = parse_config(\u0026args);\n    // --snip--\n}\n\nfn parse_config(args: \u0026[String]) -\u003e (\u0026str, \u0026str) {\n    let query = \u0026args[1];\n    let file_path = \u0026args[2];\n    (query, file_path)\n}\n```\n\n### Grouping Configuration Values  \nAt the moment, we’re `returning a tuple`, but then we immediately `break` that tuple `into individual parts` again. This is a `sign` that perhaps `we don’t` have the `right abstraction` yet.\n`Another indicator` that shows there’s room for improvement is the `config` part of `parse_config`, which implies that the `two values` we return are `related` and are both `part of one configuration` value. \n```rust\nfn main() {\n    let args: Vec\u003cString\u003e = env::args().collect();\n\n    let config = parse_config(\u0026args);\n\n    println!(\"Searching for {}\", config.query);\n    println!(\"In file {}\", config.file_path);\n\n    let contents = fs::read_to_string(config.file_path)\n        .expect(\"Should have been able to read the file\");\n\n    // --snip--\n}\n\nstruct Config {\n    query: String,\n    file_path: String,\n}\n\nfn parse_config(args: \u0026[String]) -\u003e Config {\n    let query = args[1].clone();     // need new references\n    let file_path = args[2].clone(); // clone not efficient but easy\n\n    Config { query, file_path }\n}\n```\n\u003eWe’ve added a `struct` named `Config` defined to have fields named `query` and `file_path`. The signature of `parse_config` now indicates that it returns a `Config` value. \n\n### Creating a Constructor for Config\nPurpose of the `parse_config` function is to `create` a `Config instance`, we can `change` parse_config from a `plain function` to a function named `new` that is associated with the `Config` struct. \n```rust\nfn main() {\n    let args: Vec\u003cString\u003e = env::args().collect();\n    let config = Config::new(\u0026args);\n    // --snip--\n}\n// --snip--\nimpl Config {\n    fn new(args: \u0026[String]) -\u003e Config {\n        let query = args[1].clone();\n        let file_path = args[2].clone();\n\n        Config { query, file_path }\n    }\n}\n```\n\u003e We’ve updated main where we were calling `parse_config` to instead call `Config::new`.\n\n### Fixing the Error Handling  \n\nImproving the Error Message\n```rust\n    // --snip--\n    fn new(args: \u0026[String]) -\u003e Config {\n        if args.len() \u003c 3 {\n            panic!(\"not enough arguments\");\n        }\n        // --snip--\n```\n\u003e However, we also have extraneous information we don’t want to give to our users. \n\nReturning a `Result` Instead of Calling `panic!`\n```rust\nimpl Config {\n    fn build(args: \u0026[String]) -\u003e Result\u003cConfig, \u0026'static str\u003e {\n        if args.len() \u003c 3 {\n            return Err(\"not enough arguments\");\n        }\n\n        let query = args[1].clone();\n        let file_path = args[2].clone();\n\n        Ok(Config { query, file_path })\n    }\n}\n```\n\u003e change the function name from `new` to `build` because many programmers expect new functions to never fail.\n\u003e Returning an Err value from Config::build allows the main function to handle the Result value returned from the build function and exit the process more cleanly in the error case.\n\nCalling `Config::build` and `Handling Errors`\n```rust\nuse std::process; \n\nfn main() {\n    let args: Vec\u003cString\u003e = env::args().collect();\n    let config = Config::build(\u0026args).unwrap_or_else(|err| { // closure\n        println!(\"Problem parsing arguments: {err}\"); // with |err| as argument\n        process::exit(1); // stop the program and return the number\n    });\n    // --snip--\n```\n\u003e A nonzero exit status is a convention to signal to the process that called our program that the program exited with an error state.\n\n### Extracting Logic from main\nWe’ll extract a function named `run` that will `hold` all the `logic` currently in the `main` function that `isn’t involved with` setting up `configuration` or `handling errors`.\n```rust\nfn main() {\n    // --snip--\n    println!(\"Searching for {}\", config.query);\n    println!(\"In file {}\", config.file_path);\n\n    run(config);\n}\n\nfn run(config: Config) {\n    let contents = fs::read_to_string(config.file_path)\n        .expect(\"Should have been able to read the file\");\n\n    println!(\"With text:\\n{contents}\");\n}\n// --snip--\n```\n\u003eThe run function now contains all the remaining logic from main, starting from reading the file. The run function takes the Config instance as an argument.\n\n### Returning Errors from the run Function\nWith the remaining program logic separated into the `run` function, we can `improve` the `error handling`, as we did with `Config::build` \n```rust\nuse std::error::Error;\n// --snip--\nfn run(config: Config) -\u003e Result\u003c(), Box\u003cdyn Error\u003e\u003e { // change return\n    let contents = fs::read_to_string(config.file_path)?;\n\n    println!(\"With text:\\n{contents}\");\n\n    Ok(()) // idiomatic way to indicate \n           // that we’re calling run for its side effects only;\n}\n```\n\u003e 1. We changed the return type of the run function to `Result\u003c(), Box\u003cdyn Error\u003e\u003e`. `Box\u003cdyn Error\u003e` means the function will `return` a type that implements the `Error trait`, but we `don’t have to specify` what particular `type` the return value will be.  \n\u003e 2. We’ve removed the call to `expect` in favor of the `?` operator. Rather than `panic!` on an error, `?` will `return` the `error value` from the current function for the caller to handle.\n\u003e 3. The `run` function now `returns` an `Ok` value in the success case.\n\n### Handling Errors Returned from run in main\nWe’ll check for errors and handle them using a technique similar to one we used with `Config::build`\n```rust\nfn main() {\n    // --snip--\n\n    println!(\"Searching for {}\", config.query);\n    println!(\"In file {}\", config.file_path);\n\n    if let Err(e) = run(config) {\n        println!(\"Application error: {e}\");\n        process::exit(1);\n    }\n}\n```\n\u003e We use `if let` rather than `unwrap_or_else` to check whether `run` returns an `Err` value and call `process::exit(1)` if it does.\n\n### Splitting Code into a Library Crate\nLet’s `move` all the code that isn’t the main function from src/main.rs to `src/lib.rs`:\n- The run function definition  \n- The relevant use statements  \n- The definition of Config   \n- The Config::build function definition  \n```rust\nuse std::error::Error;\nuse std::fs;\n\npub struct Config {\n    pub query: String,\n    pub file_path: String,\n}\n\nimpl Config {\n    pub fn build(args: \u0026[String]) -\u003e Result\u003cConfig, \u0026'static str\u003e {\n        // --snip--\n    }\n}\n\npub fn run(config: Config) -\u003e Result\u003c(), Box\u003cdyn Error\u003e\u003e {\n    // --snip--\n}\n```\n\u003e We’ve made liberal use of the `pub` keyword: on `Config`, on its fields and its `build` method, and on the `run` function. We now have a library crate that has a public API we can test!\n\nNow we need to bring the code we moved to `src/lib.rs` into the `scope` of the binary crate in `src/main.rs`\n```rust\nuse std::env;\nuse std::process;\n\nuse minigrep::Config;\n\nfn main() {\n    // --snip--\n    if let Err(e) = minigrep::run(config) {\n        // --snip--\n    }\n}\n```\n\n## Developing the Library’s Functionality with Test-Driven Development\nIn this section, we’ll add the searching logic to the minigrep program using the test-driven development (TDD) process with the following steps:\n1. Write a test that fails and run it to make sure it fails for the reason you expect.\n2. Write or modify just enough code to make the new test pass.\n3. Refactor the code you just added or changed and make sure the tests continue to pass.\n4. Repeat from step 1!\n\n### Writing a Failing Test\nThe test function specifies the behavior we want the `search` function to have: it will take a query and the text to search, and it will return only the lines from the text that contain the query.\n```rust\n#[cfg(test)]\nmod tests {\n    use super::*;\n\n    #[test]\n    fn one_result() {\n        let query = \"duct\";\n        let contents = \"\\\nRust:\nsafe, fast, productive.\nPick three.\";\n\n        assert_eq!(vec![\"safe, fast, productive.\"], search(query, contents));\n    }\n}\n```\nIn accordance with TDD principles, we’ll add just enough code to get the test to compile and run by adding a definition of the `search` function that always returns an empty vector\n```rust\npub fn search\u003c'a\u003e(query: \u0026str, contents: \u0026'a str) -\u003e Vec\u003c\u0026'a str\u003e {\n    vec![]\n}\n```\n\u003e with 'a we indicate that the returned vector should contain string slices that reference slices of the argument contents (rather than the argument query).\n\u003e if the compiler assumes we’re making string slices of query rather than contents, it will do its safety checking incorrectly\n\n### Writing Code to Pass the Test\nCurrently, our test is failing because we always `return` an empty vector. To fix that and implement `search`, our program needs to follow these steps:\n1. Iterate through each line of the contents.  \n2. Check whether the line contains our query string.  \n3. If it does, add it to the list of values we’re returning.  \n4. If it doesn’t, do nothing.  \n5. Return the list of results that match.  \n\nIterating Through Lines with the lines Method\n```rust\npub fn search\u003c'a\u003e(query: \u0026str, contents: \u0026'a str) -\u003e Vec\u003c\u0026'a str\u003e {\n    for line in contents.lines() {\n        // do something with line\n    }\n}\n```\n\u003e The lines method returns an `iterator`.\n\nSearching Each Line for the Query\n```rust\npub fn search\u003c'a\u003e(query: \u0026str, contents: \u0026'a str) -\u003e Vec\u003c\u0026'a str\u003e {\n    for line in contents.lines() {\n        if line.contains(query) {\n            // do something with line\n        }\n    }\n}\n```\nStoring Matching Lines\n```rust\npub fn search\u003c'a\u003e(query: \u0026str, contents: \u0026'a str) -\u003e Vec\u003c\u0026'a str\u003e {\n    let mut results = Vec::new(); // using vector for matching lines\n\n    for line in contents.lines() {\n        if line.contains(query) {\n            results.push(line);\n        }\n    }\n\n    results // return matchiing lines\n}\n```\n### Using the search Function in the run Function\nNow that the `search` function is working and tested, we need to call search from our `run` function. \n```rust\npub fn run(config: Config) -\u003e Result\u003c(), Box\u003cdyn Error\u003e\u003e {\n    let contents = fs::read_to_string(config.file_path)?;\n\n    for line in search(\u0026config.query, \u0026contents) {\n        println!(\"{line}\");\n    }\n\n    Ok(())\n}\n```\n\u003e We’re still using a for loop to `return` each line from `search` and print it.\n\n## Working with Environment Variables\nWe’ll improve `minigrep` by adding an extra feature: an option for case-insensitive searching that the user can turn on via an environment variable.\n\n### Writing a Failing Test for the Case-Insensitive search Function\nWe first add a new search_case_insensitive function that will be called when the environment variable has a value. We’ll continue to follow the TDD process, so the first step is again to write a failing test. \n```rust\n#[cfg(test)]\nmod tests {\n    use super::*;\n\n    #[test]\n    fn case_sensitive() {\n        let query = \"duct\";\n        let contents = \"\\\nRust:\nsafe, fast, productive.\nPick three.\nDuct tape.\"; // not match also\n\n        assert_eq!(vec![\"safe, fast, productive.\"], search(query, contents));\n    }\n\n    #[test]\n    fn case_insensitive() {\n        let query = \"rUsT\";\n        let contents = \"\\\nRust:\nsafe, fast, productive.\nPick three.\nTrust me.\";\n\n        assert_eq!(\n            vec![\"Rust:\", \"Trust me.\"],\n            search_case_insensitive(query, contents)\n        );\n    }\n}\n```\n\n### Implementing the search_case_insensitive Function\nThe `search_case_insensitive` function will be almost the same as the `search` function.\n```rust\npub fn search_case_insensitive\u003c'a\u003e(\n    query: \u0026str,\n    contents: \u0026'a str,\n) -\u003e Vec\u003c\u0026'a str\u003e {\n    let query = query.to_lowercase(); // shadowed\n    let mut results = Vec::new();\n\n    for line in contents.lines() {\n        if line.to_lowercase().contains(\u0026query) {\n            results.push(line);\n        }\n    }\n\n    results\n}\n```\n\u003e Note that `query` is now a `String` rather than a string slice, because calling `to_lowercase` creates new data rather than referencing existing data. \n\nWe’ll add a configuration option to the Config struct to switch between case-sensitive and case-insensitive search.\n```rust\npub struct Config {\n    pub query: String,\n    pub file_path: String,\n    pub ignore_case: bool,\n}\n```\n\nNext, we need the `run` function to check the ignore_case field’s value and use that to decide whether to call the `search` function or the `search_case_insensitive` function\n```rust\npub fn run(config: Config) -\u003e Result\u003c(), Box\u003cdyn Error\u003e\u003e {\n    let contents = fs::read_to_string(config.file_path)?;\n\n    let results = if config.ignore_case {\n        search_case_insensitive(\u0026config.query, \u0026contents)\n    } else {\n        search(\u0026config.query, \u0026contents)\n    };\n\n    for line in results {\n        println!(\"{line}\");\n    }\n\n    Ok(())\n}\n```\n\nFinally, we need to check for the environment variable.\n```rust\nuse std::env;\n// --snip--\n\nimpl Config {\n    pub fn build(args: \u0026[String]) -\u003e Result\u003cConfig, \u0026'static str\u003e {\n        if args.len() \u003c 3 {\n            return Err(\"not enough arguments\");\n        }\n\n        let query = args[1].clone();\n        let file_path = args[2].clone();\n\n        let ignore_case = env::var(\"IGNORE_CASE\").is_ok();\n\n        Ok(Config {\n            query,\n            file_path,\n            ignore_case,\n        })\n    }\n}\n```\n\u003e we create a new variable `ignore_case`. To set its value, we call the `env::var` function and pass it the name of the `IGNORE_CASE` environment variable.\n\nNow, let’s run the program with `IGNORE_CASE` set to `1` but with the same `query` to\n```sh\nIGNORE_CASE=1 cargo run -- to poem.txt\n```\n\n## Writing Error Messages to Standard Error Instead of Standard Output\nIn most terminals, there are two kinds of output: standard output (`stdout`) for general information and standard error (`stderr`) for error messages. \n\n### Checking Where Errors Are Written\nCommand line programs are expected to send error messages to the standard error stream so we can still see error messages on the screen even if we redirect the standard output stream to a file. \n```sh\ncargo run \u003e output.txt\n```\n\n### Printing Errors to Standard Error\nThe standard library provides the `eprintln!` macro that prints to the standard error stream\n```rust\nfn main() {\n    let args: Vec\u003cString\u003e = env::args().collect();\n\n    let config = Config::build(\u0026args).unwrap_or_else(|err| {\n        eprintln!(\"Problem parsing arguments: {err}\");\n        process::exit(1);\n    });\n\n    if let Err(e) = minigrep::run(config) {\n        eprintln!(\"Application error: {e}\");\n        process::exit(1);\n    }\n}\n```\n\u003e now using standard output for successful output and standard error for error output as appropriate.\n\n# Functional Language Features\nProgramming in a functional style often includes using functions as values by passing them in arguments, returning them from other functions, assigning them to variables for later execution, and so forth.\n\n## Closures: Anonymous Functions that Capture Their Environment\nRust’s closures are anonymous functions you can save in a variable or pass as arguments to other functions.\n\n### Capturing the Environment with Closures\nFor this example, we’re going to use an enum called ShirtColor that has the variants `Red` and `Blue` (limiting the number of colors available for simplicity). We represent the company’s `inventory` with an Inventory struct that has a field named `shirts` that contains a `Vec\u003cShirtColor\u003e` representing the shirt colors currently in stock. The method `giveaway` defined on `Inventory` gets the optional shirt color preference of the free shirt winner, and returns the shirt color the person will get.\n```rust\n#[derive(Debug, PartialEq, Copy, Clone)]\nenum ShirtColor {\n    Red,\n    Blue,\n}\n\nstruct Inventory {\n    shirts: Vec\u003cShirtColor\u003e,\n}\n\nimpl Inventory {\n    fn giveaway(\u0026self, user_preference: Option\u003cShirtColor\u003e) -\u003e ShirtColor {\n        // passed a closure that calls self.most_stocked()\n        // on the current Inventory instance\n        // The standard library didn’t need to know anything\n        // about the Inventory or ShirtColor types we defined,\n        // Functions, on the other hand, \n        // are not able to capture their environment in this way.\n        user_preference.unwrap_or_else(|| self.most_stocked())\n    }\n\n    fn most_stocked(\u0026self) -\u003e ShirtColor {\n        let mut num_red = 0;\n        let mut num_blue = 0;\n\n        for color in \u0026self.shirts {\n            match color {\n                ShirtColor::Red =\u003e num_red += 1,\n                ShirtColor::Blue =\u003e num_blue += 1,\n            }\n        }\n        if num_red \u003e num_blue {\n            ShirtColor::Red\n        } else {\n            ShirtColor::Blue\n        }\n    }\n}\n```\n\n### Closure Type Inference and Annotation\nClosures don’t usually require you to annotate the types of the parameters or the return value like `fn` functions do.\nClosures are typically short and relevant only within a narrow context rather than in any arbitrary scenario. \nAs with variables, we can add type annotations if we want to increase explicitness and clarity at the cost of being more verbose than is strictly necessary.\n```rust\n    let expensive_closure = |num: u32| -\u003e u32 {\n        println!(\"calculating slowly...\");\n        thread::sleep(Duration::from_secs(2));\n        num\n    };\n```\nThis illustrates how closure syntax is similar to function syntax except for the use of pipes and the amount of syntax that is optional:\n```rust\nfn  add_one_v1   (x: u32) -\u003e u32 { x + 1 }\nlet add_one_v2 = |x: u32| -\u003e u32 { x + 1 };\nlet add_one_v3 = |x|             { x + 1 };\nlet add_one_v4 = |x|               x + 1  ;\n```\nBecause there are no type annotations, we can call the closure with any type, which we’ve done here with `String` the first time. If we then try to call example_closure with an `integer`, we’ll get an error.\n```rust\n    let example_closure = |x| x;\n\n    let s = example_closure(String::from(\"hello\"));\n    let n = example_closure(5); // error here, cant use second time\n```\n\n### Capturing References or Moving Ownership\nClosures can capture values from their environment in three ways, which directly map to the three ways a function can take a parameter: \n- borrowing immutably  \n- borrowing mutably  \n- taking ownership  \n\nA closure that captures an immutable reference to the vector named `list` because it only needs an immutable reference to print the value:\n```rust\nfn main() {\n    let list = vec![1, 2, 3];\n    println!(\"Before defining closure: {:?}\", list);\n\n    let only_borrows = || println!(\"From closure: {:?}\", list); // bind closure\n\n    println!(\"Before calling closure: {:?}\", list);\n    only_borrows(); // using closure\n    println!(\"After calling closure: {:?}\", list);\n}\n```\n\u003e Because we can have multiple immutable references to list at the same time, list is still accessible from the code before the closure definition, after the closure definition but before the closure is called, and after the closure is called. \n\nwe change the closure body so that it adds an element to the list vector. The closure now captures a mutable reference\n```rust\nfn main() {\n    let mut list = vec![1, 2, 3];\n    println!(\"Before defining closure: {:?}\", list);\n\n    let mut borrows_mutably = || list.push(7); // borrow bind with mut\n    // no printing here because borrowing\n    borrows_mutably();\n    println!(\"After calling closure: {:?}\", list);\n}\n```\n\u003e Note that there’s no longer a `println!` between the definition and the call of the `borrows_mutably` closure: when `borrows_mutably` is defined, it captures a mutable reference to `list`\n\nIf you want to force the closure to take ownership of the values it uses in the environment even though the body of the closure doesn’t strictly need ownership, you can use the `move` keyword before the parameter list.\n```rust\nuse std::thread;\n\nfn main() {\n    let list = vec![1, 2, 3];\n    println!(\"Before defining closure: {:?}\", list);\n\n    thread::spawn(move || println!(\"From thread: {:?}\", list))\n        .join()\n        .unwrap();\n}\n```\n\u003e This technique is mostly useful when passing a closure to a new `thread` to move the data so that it’s owned by the new thread.\n\u003e If the main thread maintained ownership of list but ended before the new thread did and dropped list, the immutable reference in the thread would be invalid. \n\n### Moving Captured Values Out of Closures and the Fn Traits\nA closure body can do any of the following: move a captured value out of the closure, mutate the captured value, neither move nor mutate the value, or capture nothing from the environment to begin with.\nThe way a closure captures and handles values from the environment affects which traits the closure implements:\n1. `FnOnce` applies to closures that can be called once\n2. `FnMut` applies to closures that don’t move captured values out of their body, but that might mutate the captured values. \n3. `Fn` applies to closures that don’t move captured values out of their body and that don’t mutate captured values, as well as closures that capture nothing from their environment.\n\nLet’s look at the definition of the unwrap_or_else method on Option\u003cT\u003e\n```rust\nimpl\u003cT\u003e Option\u003cT\u003e {\n    pub fn unwrap_or_else\u003cF\u003e(self, f: F) -\u003e T\n    where\n        F: FnOnce() -\u003e T\n    {\n        match self {\n            Some(x) =\u003e x,\n            None =\u003e f(),\n        }\n    }\n}\n```\n\u003e The trait bound specified on the generic type `F` is `FnOnce() -\u003e T`, which means `F` must be able to be called once, take no arguments, and return a `T`. Because all closures implement `FnOnce`, `unwrap_or_else` accepts the most different kinds of closures and is as flexible as it can be.\n\nNote: Functions can implement all three of the `Fn` traits too. If what we want to do doesn’t require capturing a value from the environment, we can use the name of a function rather than a closure where we need something that implements one of the `Fn` traits. For example, on an `Option\u003cVec\u003cT\u003e\u003e` value, we could call `unwrap_or_else(Vec::new)` to get a new, empty vector if the value is `None`.\n\nNow let’s look at the standard library method `sort_by_key` defined on slices, to see how that differs from `unwrap_or_else` and why `sort_by_key` uses `FnMut` instead of `FnOnce` for the trait bound. \n```rust\n#[derive(Debug)]\nstruct Rectangle {\n    width: u32,\n    height: u32,\n}\n\nfn main() {\n    let mut list = [\n        Rectangle { width: 10, height: 1 },\n        Rectangle { width: 3, height: 5 },\n        Rectangle { width: 7, height: 12 },\n    ];\n\n    list.sort_by_key(|r| r.width);\n    println!(\"{:#?}\", list);\n}\n```\n\n## Processing a Series of Items with Iterators\nThe iterator pattern allows you to perform some task on a sequence of items in turn. In Rust, iterators are `lazy`, meaning they have no effect until you call methods that consume the iterator to use it up.\n```rust\n    let v1 = vec![1, 2, 3];\n    let v1_iter = v1.iter();\n```\nWhen the for loop is called using the iterator in v1_iter, each element in the iterator is used in one iteration of the loop, which prints out each value.\n```rust\n    let v1 = vec![1, 2, 3];\n\n    let v1_iter = v1.iter();\n\n    for val in v1_iter {\n        println!(\"Got: {}\", val);\n    }\n```\n\n### The Iterator Trait and the next Method\nAll iterators implement a trait named Iterator that is defined in the standard library. \n```rust\npub trait Iterator {\n    type Item;\n\n    fn next(\u0026mut self) -\u003e Option\u003cSelf::Item\u003e;\n\n    // methods with default implementations elided\n}\n```\n\u003e type Item: this code says implementing the Iterator trait requires that you also define an Item type, and this Item type is used in the return type of the next method. In other words, the Item type will be the type returned from the iterator.\n\nWe can call the next method on iterators directly\n```rust\n    #[test]\n    fn iterator_demonstration() {\n        let v1 = vec![1, 2, 3];\n\n        let mut v1_iter = v1.iter();\n\n        assert_eq!(v1_iter.next(), Some(\u00261));\n        assert_eq!(v1_iter.next(), Some(\u00262));\n        assert_eq!(v1_iter.next(), Some(\u00263));\n        assert_eq!(v1_iter.next(), None);\n    }\n```\n\u003e Note that we needed to make `v1_iter` mutable: calling the `next` method on an iterator changes internal state that the iterator uses to keep track of where it is in the sequence. In other words, this code consumes, or uses up, the iterator. Each call to `next` eats up an item from the iterator. We didn’t need to make `v1_iter` mutable when we used a `for` loop because the loop took ownership of `v1_iter` and made it mutable behind the scenes.\n\nAlso note that the values we get from the calls to `next` are immutable references to the values in the vector. The `iter` method produces an iterator over immutable references. If we want to create an iterator that takes ownership of `v1` and returns owned values, we can call `into_iter` instead of iter. Similarly, if we want to iterate over mutable references, we can call `iter_mut` instead of `iter`.\n\n### Methods that Consume the Iterator\nMethods that call `next` are called `consuming adaptors`, because calling them uses up the iterator. One example is the `sum` method\n```rust\n    #[test]\n    fn iterator_sum() {\n        let v1 = vec![1, 2, 3];\n\n        let v1_iter = v1.iter();\n\n        let total: i32 = v1_iter.sum();\n\n        assert_eq!(total, 6);\n    }\n```\n\n### Methods that Produce Other Iterators\n`Iterator adaptors` are methods defined on the `Iterator` trait that don’t consume the iterator. The `map` method returns a new iterator that produces the modified items. \n```rust\n    let v1: Vec\u003ci32\u003e = vec![1, 2, 3];\n    // map will produce new iterator\n    // we need to collect items from it\n    let v2: Vec\u003c_\u003e = v1.iter().map(|x| x + 1).collect();\n\n    assert_eq!(v2, vec![2, 3, 4]);\n```\n\n### Using Closures that Capture Their Environment\nMany iterator adapters take closures as arguments, and commonly the closures we’ll specify as arguments to iterator adapters will be closures that capture their environment.\n```rust\n#[derive(PartialEq, Debug)]\nstruct Shoe {\n    size: u32,\n    style: String,\n}\n\nfn shoes_in_size(shoes: Vec\u003cShoe\u003e, shoe_size: u32) -\u003e Vec\u003cShoe\u003e {\n    // takes ownership of a vector of shoes and a shoe size as parameters\n    shoes.into_iter().filter(|s| s.size == shoe_size).collect()\n}\n\n#[cfg(test)]\nmod tests {\n    use super::*;\n\n    #[test]\n    fn filters_by_size() {\n        let shoes = vec![\n            Shoe {\n                size: 10,\n                style: String::from(\"sneaker\"),\n            },\n            Shoe {\n                size: 13,\n                style: String::from(\"sandal\"),\n            },\n            Shoe {\n                size: 10,\n                style: String::from(\"boot\"),\n            },\n        ];\n\n        let in_my_size = shoes_in_size(shoes, 10);\n\n        assert_eq!(\n            in_my_size,\n            vec![\n                Shoe {\n                    size: 10,\n                    style: String::from(\"sneaker\")\n                },\n                Shoe {\n                    size: 10,\n                    style: String::from(\"boot\")\n                },\n            ]\n        );\n    }\n}\n```\n\u003e The closure captures the shoe_size parameter from the environment and compares the value with each shoe’s size, keeping only shoes of the size specified. Finally, calling collect gathers the values returned by the adapted iterator into a vector that’s returned by the function.\n\n\n## Improving Our I/O Project\nLet’s look at how iterators can improve our implementation of the `Config::build` function and the `search` function.\n\n### Removing a clone Using an Iterator\nWith our new knowledge about iterators, we can change the `build` function to take ownership of an iterator as its argument instead of borrowing a slice. \n```rust\nimpl Config {\n    pub fn build(args: \u0026[String]) -\u003e Result\u003cConfig, \u0026'static str\u003e {\n        if args.len() \u003c 3 {\n            return Err(\"not enough arguments\");\n        }\n\n        let query = args[1].clone();\n        let file_path = args[2].clone();\n\n        let ignore_case = env::var(\"IGNORE_CASE\").is_ok();\n\n        Ok(Config {\n            query,\n            file_path,\n            ignore_case,\n        })\n    }\n}\n```\n\u003e Once `Config::build` takes ownership of the iterator and stops using indexing operations that borrow, we can move the `String` values from the iterator into `Config` rather than calling `clone` and making a new allocation.\n\n### Using the Returned Iterator Directly\nChange main function\n```rust\nfn main() {\n    let config = Config::build(env::args()).unwrap_or_else(|err| {\n        eprintln!(\"Problem parsing arguments: {err}\");\n        process::exit(1);\n    });\n\n    // --snip--\n}\n```\n\u003e The `env::args` function returns an iterator! Rather than collecting the iterator values into a vector and then passing a slice to `Config::build`, now we’re passing ownership of the iterator returned from `env::args` to `Config::build` directly.\n\nChange lib\n```rust\nimpl Config {\n    pub fn build(\n        mut args: impl Iterator\u003cItem = String\u003e,\n    ) -\u003e Result\u003cConfig, \u0026'static str\u003e {\n        // --snip--\n```\n\u003e The standard library documentation for the `env::args` function shows that the type of the iterator it returns is `std::env::Args`, and that type implements the `Iterator` trait and returns `String` values.\n\n### Using Iterator Trait Methods Instead of Indexing\nNext, we’ll fix the body of Config::build. Because args implements the Iterator trait, we know we can call the next method on it! \n```rust\nimpl Config {\n    pub fn build(\n        mut args: impl Iterator\u003cItem = String\u003e,\n    ) -\u003e Result\u003cConfig, \u0026'static str\u003e {\n        args.next();\n\n        let query = match args.next() {\n            Some(arg) =\u003e arg,\n            None =\u003e return Err(\"Didn't get a query string\"),\n        };\n\n        let file_path = match args.next() {\n            Some(arg) =\u003e arg,\n            None =\u003e return Err(\"Didn't get a file path\"),\n        };\n\n        let ignore_case = env::var(\"IGNORE_CASE\").is_ok();\n\n        Ok(Config {\n            query,\n            file_path,\n            ignore_case,\n        })\n    }\n}\n```\n\n### Making Code Clearer with Iterator Adaptors\nWe can also take advantage of iterators in the `search` function in our I/O project\n```rust\npub fn search\u003c'a\u003e(query: \u0026str, contents: \u0026'a str) -\u003e Vec\u003c\u0026'a str\u003e {\n    let mut results = Vec::new();\n\n    for line in contents.lines() {\n        if line.contains(query) {\n            results.push(line);\n        }\n    }\n\n    results\n}\n```\nWe can write this code in a more concise way using iterator adaptor methods. Doing so also lets us avoid having a mutable intermediate `results` vector. The functional programming style prefers to minimize the amount of mutable state to make code clearer. \n```rust\npub fn search\u003c'a\u003e(query: \u0026str, contents: \u0026'a str) -\u003e Vec\u003c\u0026'a str\u003e {\n    contents\n        .lines()\n        .filter(|line| line.contains(query))\n        .collect()\n}\n```\n\u003e uses the filter `adaptor` to keep only the lines that `line.contains(query)` returns `true` for. We then collect the matching lines into another vector with `collect`.\n\n### Choosing Between Loops or Iterators\nMost Rust programmers prefer to use the `iterator style`. It’s a bit tougher to get the hang of at first, but once you get a feel for the various iterator adaptors and what they do, iterators can be easier to understand.\n\n## Comparing Performance: Loops vs. Iterators\nTo determine whether to use loops or iterators, you need to know which implementation is faster: the version of the search function with an explicit for loop or the version with iterators.\n```rust\ntest bench_search_for  ... bench:  19,620,300 ns/iter (+/- 915,700)\ntest bench_search_iter ... bench:  19,234,900 ns/iter (+/- 657,200)\n```\n\u003e The iterator version was slightly faster!\n\n# More About Cargo\n\n## Customizing Builds with Release Profiles\nIn Rust, release profiles are predefined and customizable profiles with different configurations that allow a programmer to have more control over various options for compiling code\n```sh\n$ cargo build\n    Finished dev [unoptimized + debuginfo] target(s) in 0.0s\n$ cargo build --release\n    Finished release [optimized] target(s) in 0.0s\n```\nCargo has default settings for each of the profiles that apply when you haven't explicitly added any `[profile.*]` sections in the project’s `Cargo.toml file`. \n```\n[profile.dev]\nopt-level = 0\n\n[profile.release]\nopt-level = 3\n```\n\n## Publishing a Crate to Crates.io\nWe’ve used packages from crates.io as dependencies of our project, but you can also share your code with other people by publishing your own packages.\n\n### Making Useful Documentation Comments\nDocumentation comments use three slashes, ///, instead of two and support Markdown notation for formatting the text.\n```rust\n/// Adds one to the number given.\n///\n/// # Examples\n///\n/// ```\n/// let arg = 5;\n/// let answer = my_crate::add_one(arg);\n///\n/// assert_eq!(6, answer);\n/// ```\npub fn add_one(x: i32) -\u003e i32 {\n    x + 1\n}\n```\n\u003e For convenience, running `cargo doc --open` will build the HTML for your current crate’s documentation \n\n### Commonly Used Sections\nHere are some other sections that crate authors commonly use in their documentation:\n- `# Examples`\n- `# Panics`\n- `# Errors`\n- `# Safety`\n\n### Documentation Comments as Tests\nAdding example code blocks in your documentation comments can help demonstrate how to use your library, and doing so has an additional bonus: running `cargo test` will run the code examples in your documentation as tests!\n\n### Commenting Contained Items\nThe style of doc comment `//!` adds documentation to the item that contains the comments rather than to the items following the comments.\n```rust\n//! # My Crate\n//!\n//! `my_crate` is a collection of utilities to make performing certain\n//! calculations more convenient.\n\n/// Adds one to the number given.\n// --snip--\n```\n\n### Exporting a Convenient Public API with pub use\nTo remove the internal organization from the public API, we can add `pub use` statements to re-export the items at the top level\n```rust\n//! # Art\n//!\n//! A library for modeling artistic concepts.\n\npub use self::kinds::PrimaryColor;\npub use self::kinds::SecondaryColor;\npub use self::utils::mix;\n\npub mod kinds {\n    // --snip--\n}\n\npub mod utils {\n    // --snip--\n}\n```\n\n### Setting Up a Crates.io Account\nBefore you can publish any crates, you need to create an account on crates.io and get an API token. \n```sh\ncargo login abcdefghijklmnopqrstuvwxyz012345\n```\n\n### Adding Metadata to a New Crate\nLet’s say you have a crate you want to publish. Before publishing, you’ll need to add some metadata in the [package] section of the crate’s Cargo.toml file.\n```\n[package]\nname = \"guessing_game\"\nversion = \"0.1.0\"\nedition = \"2021\"\ndescription = \"A fun game where you guess what number the computer has chosen.\"\nlicense = \"MIT OR Apache-2.0\"\n\n[dependencies]\n```\n\n### Publishing to Crates.io\nBe careful, because a publish is permanent. The version can never be overwritten, and the code cannot be deleted. \n```sh\ncargo publish\n```\n\n### Publishing a New Version of an Existing Crate\nWhen you’ve made changes to your crate and are ready to release a new version, you change the version value specified in your Cargo.toml file and republish.\n\n### Deprecating Versions from Crates.io with cargo yank\nAlthough you can’t remove previous versions of a crate, you can prevent any future projects from adding them as a new dependency.\n```\n$ cargo yank --vers 1.0.1\n    Updating crates.io index\n        Yank guessing_game@1.0.1\n```\n\n## Cargo Workspaces\nCargo offers a feature called workspaces that can help manage multiple related packages that are developed in tandem.\n\n### Creating a Workspace\nA workspace is a set of packages that share the same Cargo.lock and output directory. \n```\n[workspace]\n\nmembers = [\n    \"adder\",\n]\n\n$ cargo new adder\n     Created binary (application) `adder` package\n\n├── Cargo.lock\n├── Cargo.toml\n├── adder\n│   ├── Cargo.toml\n│   └── src\n│       └── main.rs\n└── target\n```\n\n### Creating the Second Package in the Workspace\nNext, let’s create another member package in the workspace and call it add_one. Change the top-level Cargo.toml to specify the add_one path in the members list:\n```\n[workspace]\n\nmembers = [\n    \"adder\",\n    \"add_one\",\n]\n\n$ cargo new add_one --lib\n     Created library `add_one` package\n\n├── Cargo.lock\n├── Cargo.toml\n├── add_one\n│   ├── Cargo.toml\n│   └── src\n│       └── lib.rs\n├── adder\n│   ├── Cargo.toml\n│   └── src\n│       └── main.rs\n└── target\n\n```\n\nIn the add_one/src/lib.rs file, let’s add an add_one function:\n```rust\npub fn add_one(x: i32) -\u003e i32 {\n    x + 1\n}\n```\n\nNow we can have the adder package with our binary depend on the add_one package that has our library.\n```\n[dependencies]\nadd_one = { path = \"../add_one\" }\n```\n\nNext, let’s use the add_one function (from the add_one crate) in the adder crate. \n```rust\nuse add_one;\n\nfn main() {\n    let num = 10;\n    println!(\"Hello, world! {num} plus one is {}!\", add_one::add_one(num));\n}\n```\n\nTo run the binary crate from the add directory, we can specify which package in the workspace we want to run by using the -p argument and the package name with cargo run\n```\n$ cargo run -p adder\n    Finished dev [unoptimized + debuginfo] target(s) in 0.0s\n     Running `target/debug/adder`\nHello, world! 10 plus one is 11!\n```\n\n### Depending on an External Package in a Workspace\nNotice that the workspace has only one Cargo.lock file at the top level, rather than having a Cargo.lock in each crate’s directory. \n\n### Adding a Test to a Workspace\nFor another enhancement, let’s add a test of the add_one::add_one function within the add_one crate:\n```rust\npub fn add_one(x: i32) -\u003e i32 {\n    x + 1\n}\n\n#[cfg(test)]\nmod tests {\n    use super::*;\n\n    #[test]\n    fn it_works() {\n        assert_eq!(3, add_one(2));\n    }\n}\n```\n\u003e Now run cargo test in the top-level add directory. Running cargo test in a workspace structured like this one will run the tests for all the crates in the workspace\n\nWe can also run tests for one particular crate in a workspace from the top-level directory by using the -p flag and specifying the name of the crate we want to test:\n```sh\ncargo test -p add_one\n```\n\n## Installing Binaries with cargo install\nThe cargo install command allows you to install and use binary crates locally. \n```sh\ncargo install ripgrep\n```\n\n## Extending Cargo with Custom Commands\nCargo is designed so you can extend it with new subcommands without having to modify Cargo. If a binary in your $PATH is named cargo-something, you can run it as if it was a Cargo subcommand by running cargo something. Custom commands like this are also listed when you run cargo --list. Being able to use cargo install to install extensions and then run them just like the built-in Cargo tools is a super convenient benefit of Cargo’s design!\n\n# Smart Pointers\nA pointer is a general concept for a variable that contains an address in memory. This address refers to, or “points at,” some other data. \n1. `Box\u003cT\u003e` for allocating values on the heap\n2. `Rc\u003cT\u003e` a reference counting type that enables multiple ownership\n3. `Ref\u003cT\u003e and RefMut\u003cT\u003e` accessed through `RefCell\u003cT\u003e`, a type that enforces the borrowing rules at runtime instead of compile time\n\n## Using Box\u003cT\u003e to Point to Data on the Heap\nBoxes don’t have performance overhead, other than storing their data on the heap instead of on the stack. But they don’t have many extra capabilities either. \n\n### Using a Box\u003cT\u003e to Store Data on the Heap\nuse a box to store an i32 value on the heap:\n```rust\nfn main() {\n    let b = Box::new(5);\n    println!(\"b = {}\", b);\n}\n```\n\n### Enabling Recursive Types with Boxes\nA value of recursive type can have another value of the same type as part of itself. \n\nMore Information About the Cons List\n```rust\n// representing recursive list from Lisp language\n(1, (2, (3, Nil))) \n\n// recreate in rust\nenum List { \n    Cons(i32, List),\n    Nil,\n}\n\n// using recursive list\nuse crate::List::{Cons, Nil}; \n\nfn main() {\n    let list = Cons(1, Cons(2, Cons(3, Nil)));\n}\n```\n\n### Using Box\u003cT\u003e to Get a Recursive Type with a Known Size\nBecause a Box\u003cT\u003e is a pointer, Rust always knows how much space a Box\u003cT\u003e needs: a pointer’s size doesn’t change based on the amount of data it’s pointing to. This means we can put a Box\u003cT\u003e inside the Cons variant instead of another List value directly. \n```rust\nenum List {\n    Cons(i32, Box\u003cList\u003e),\n    Nil,\n}\n\nuse crate::List::{Cons, Nil};\n\n// using Box\u003ct\u003e to store recursive list\nfn main() {\n    let list = Cons(1, Box::new(Cons(2, Box::new(Cons(3, Box::new(Nil))))));\n}\n```\n\n## Treating Smart Pointers Like Regular References with the Deref Trait\nImplementing the Deref trait allows you to customize the behavior of the dereference operator `*` \n\n### Following the Pointer to the Value\nwe create a reference to an i32 value and then use the dereference operator to follow the reference to the value\n```rust\nfn main() {\n    let x = 5;\n    let y = \u0026x; // use ref\n\n    assert_eq!(5, x);\n    assert_eq!(5, *y); // deref pointer\n}\n```\n\n### Using Box\u003cT\u003e Like a Reference\nWe can rewrite the code in Listing 15-6 to use a Box\u003cT\u003e instead of a reference;\n```rust\nfn main() {\n    let x = 5;\n    let y = Box::new(x); // use Box\n\n    assert_eq!(5, x);\n    assert_eq!(5, *y);\n}\n```\n\n### Defining Our Own Smart Pointer\nLet’s build a smart pointer similar to the Box\u003cT\u003e type provided by the standard library to experience how smart pointers behave differently from references by default\n```rust\nstruct MyBox\u003cT\u003e(T);\n\nimpl\u003cT\u003e MyBox\u003cT\u003e {\n    fn new(x: T) -\u003e MyBox\u003cT\u003e {\n        MyBox(x)\n    }\n}\n```\n\u003e Our `MyBox\u003cT\u003e` type can’t be dereferenced because we haven’t implemented that ability on our type. To enable dereferencing with the `*` operator, we implement the `Deref` trait.\n\n### Treating a Type Like a Reference by Implementing the Deref Trait\nThe Deref trait, provided by the standard library, requires us to implement one method named deref that borrows self and returns a reference to the inner data.\n```rust\nuse std::ops::Deref;\n\nimpl\u003cT\u003e Deref for MyBox\u003cT\u003e {\n    type Target = T;\n\n    fn deref(\u0026self) -\u003e \u0026Self::Target {\n        \u0026self.0\n    }\n}\n```\n\nWhen we entered *y in Listing 15-9, behind the scenes Rust actually ran this code:\n```rust\n*(y.deref())\n```\n\n### Implicit Deref Coercions with Functions and Methods\nDeref coercion converts a reference to a type that implements the `Deref` trait into a reference to another type.\n```rust\nfn hello(name: \u0026str) {\n    println!(\"Hello, {name}!\");\n}\n\nfn main() {\n    let m = MyBox::new(String::from(\"Rust\"));\n    hello(\u0026m);\n}\n```\n\u003e Here we’re calling the `hello` function with the argument `\u0026m`, which is a reference to a `MyBox\u003cString\u003e` value. Because we implemented the `Deref` trait on `MyBox\u003cT\u003e`, Rust can turn `\u0026MyBox\u003cString\u003e` into `\u0026String` by calling `deref`. The standard library provides an implementation of `Deref` on `String` that returns a string slice, and this is in the API documentation for Deref. Rust calls deref again to turn the `\u0026String` into `\u0026str`, which matches the hello function’s definition.\n\nIf Rust didn’t implement deref coercion\n```rust\nfn main() {\n    let m = MyBox::new(String::from(\"Rust\"));\n    hello(\u0026(*m)[..]);\n}\n```\n\n### How Deref Coercion Interacts with Mutability\nRust does deref coercion when it finds types and trait implementations in three cases:\n1. From `\u0026T` to \u0026U when T: Deref\u003cTarget=U\u003e\n2. From `\u0026mut T` to \u0026mut U when T: DerefMut\u003cTarget=U\u003e\n3. From `\u0026mut T` to \u0026U when T: Deref\u003cTarget=U\u003e\n\n## Running Code on Cleanup with the Drop Trait\nThe second trait important to the smart pointer pattern is `Drop`, which lets you customize what happens when a value is about to go out of scope.\n\nRust automatically called `drop` for us when our instances went out of scope, calling the code we specified. Variables are dropped in the `reverse order`\n\n### Dropping a Value Early with std::mem::drop\nUnfortunately, it’s not straightforward to disable the automatic `drop` functionality. Disabling drop isn’t usually `necessary`\nSo, if we need to force a value to be cleaned up early, we use the `std::mem::drop` function.\n\n## Rc\u003cT\u003e, the Reference Counted Smart Pointer\nIn the majority of cases, ownership is clear: you know exactly which variable owns a given value. However, there are cases when a single value might have multiple owners\n\n### Using Rc\u003cT\u003e to Share Data\nWe’ll create list a that contains 5 and then 10. Then we’ll make two more lists: b that starts with 3 and c that starts with 4. Both b and c lists will then continue on to the first a list containing 5 and 10. \n```rust\nenum List {\n    Cons(i32, Box\u003cList\u003e),\n    Nil,\n}\n\nuse crate::List::{Cons, Nil};\n\nfn main() {\n    let a = Cons(5, Box::new(Cons(10, Box::new(Nil))));\n    let b = Cons(3, Box::new(a));\n    let c = Cons(4, Box::new(a));\n}\n```\n\u003e The Cons variants own the data they hold, so when we create the b list, a is moved into b and b owns a. Then, when we try to use a again when creating c, we’re not allowed to because a has been moved.\n\nwe’ll change our definition of List to use Rc\u003cT\u003e in place of Box\u003cT\u003e\n```rust\nenum List {\n    Cons(i32, Rc\u003cList\u003e), // change to Rc\u003cT\u003e\n    Nil,\n}\n\nuse crate::List::{Cons, Nil};\nuse std::rc::Rc;\n\nfn main() {\n    let a = Rc::new(Cons(5, Rc::new(Cons(10, Rc::new(Nil)))));\n    let b = Cons(3, Rc::clone(\u0026a));\n    let c = Cons(4, Rc::clone(\u0026a));\n}\n```\n\u003e When looking for performance problems in the code, we only need to consider the deep-copy clones and can disregard calls to Rc::clone\n\n### Cloning an Rc\u003cT\u003e Increases the Reference Count\nVia immutable references, `Rc\u003cT\u003e` allows you to share data between multiple parts of your program for reading only. If `Rc\u003cT\u003e` allowed you to have multiple mutable references too, you might violate one of the borrowing rules discussed in Chapter 4: multiple mutable borrows to the same place can cause data races and inconsistencies.\n\n## RefCell\u003cT\u003e and the Interior Mutability Pattern\nInterior mutability is a design pattern in Rust that allows you to mutate data even when there are immutable references to that data; normally, this action is disallowed by the borrowing rules. \n\n### Enforcing Borrowing Rules at Runtime with RefCell\u003cT\u003e\nWith references and `Box\u003cT\u003e`, the borrowing rules’ invariants are enforced at compile time. With `RefCell\u003cT\u003e`, these invariants are enforced at runtime. With references, if you break these rules, you’ll get a compiler error. With `RefCell\u003cT\u003e`, if you break these rules, your program will panic and exit.\n\nHere is a recap of the reasons to choose `Box\u003cT\u003e`, `Rc\u003cT\u003e`, or `RefCell\u003cT\u003e`:\n- Rc\u003cT\u003e enables multiple owners of the same data; Box\u003cT\u003e and RefCell\u003cT\u003e have single owners  \n- Box\u003cT\u003e allows immutable or mutable borrows checked at compile time; Rc\u003cT\u003e allows only immutable borrows checked at compile time; RefCell\u003cT\u003e allows immutable or mutable borrows checked at runtime.  \n- Because RefCell\u003cT\u003e allows mutable borrows checked at runtime, you can mutate the value inside the RefCell\u003cT\u003e even when the RefCell\u003cT\u003e is immutable.  \n\n### Interior Mutability: A Mutable Borrow to an Immutable Value\nA consequence of the borrowing rules is that when you have an immutable value, you can’t borrow it mutably.\n```rust\nfn main() {\n    let x = 5;\n    let y = \u0026mut x; // don't work\n}\n```\n\n### A Use Case for Interior Mutability: Mock Objects\nSometimes during testing a programmer will use a type in place of another type, in order to observe particular behavior and assert it’s implemented correctly. This placeholder type is called a test double. - `stunt double` from filmmaking\n\nHere’s the scenario we’ll test: we’ll create a library that tracks a value against a maximum value and sends messages based on how close to the maximum value the current value is.\n```rust\npub trait Messenger {\n    fn send(\u0026self, msg: \u0026str);\n}\n\npub struct LimitTracker\u003c'a, T: Messenger\u003e {\n    messenger: \u0026'a T,\n    value: usize,\n    max: usize,\n}\n\nimpl\u003c'a, T\u003e LimitTracker\u003c'a, T\u003e\nwhere\n    T: Messenger,\n{\n    pub fn new(messenger: \u0026'a T, max: usize) -\u003e LimitTracker\u003c'a, T\u003e {\n        LimitTracker {\n            messenger,\n            value: 0,\n            max,\n        }\n    }\n\n    pub fn set_value(\u0026mut self, value: usize) {\n        self.value = value;\n\n        let percentage_of_max = self.value as f64 / self.max as f64;\n\n        if percentage_of_max \u003e= 1.0 {\n            self.messenger.send(\"Error: You are over your quota!\");\n        } else if percentage_of_max \u003e= 0.9 {\n            self.messenger\n                .send(\"Urgent warning: You've used up over 90% of your quota!\");\n        } else if percentage_of_max \u003e= 0.75 {\n            self.messenger\n                .send(\"Warning: You've used up over 75% of your quota!\");\n        }\n    }\n}\n```\n\u003e One important part of this code is that the Messenger trait has one method called send that takes an immutable reference to self and the text of the message. This trait is the interface our mock object needs to implement so that the mock can be used in the same way a real object is. \n\nWe need a mock object that, instead of sending an email or text message when we call send, will only keep track of the messages it’s told to send. \n```rust\n#[cfg(test)]\nmod tests {\n    use super::*;\n\n    struct MockMessenger {\n        sent_messages: Vec\u003cString\u003e,\n    }\n\n    impl MockMessenger {\n        fn new() -\u003e MockMessenger {\n            MockMessenger {\n                sent_messages: vec![],\n            }\n        }\n    }\n\n    impl Messenger for MockMessenger {\n        fn send(\u0026self, message: \u0026str) {\n            self.sent_messages.push(String::from(message));\n        }\n    }\n\n    #[test]\n    fn it_sends_an_over_75_percent_warning_message() {\n        let mock_messenger = MockMessenger::new();\n        let mut limit_tracker = LimitTracker::new(\u0026mock_messenger, 100);\n\n        limit_tracker.set_value(80);\n\n        assert_eq!(mock_messenger.sent_messages.len(), 1);\n    }\n}\n```\n\u003e This test code defines a MockMessenger struct that has a sent_messages field with a Vec of String values to keep track of the messages it’s told to send.\n\nThis is a situation in which interior mutability can help! We’ll store the sent_messages within a RefCell\u003cT\u003e, and then the send method will be able to modify sent_messages to store the messages we’ve seen. \n```rust\n#[cfg(test)]\nmod tests {\n    use super::*;\n    use std::cell::RefCell;\n\n    struct MockMessenger {\n        sent_messages: RefCell\u003cVec\u003cString\u003e\u003e,\n    }\n\n    impl MockMessenger {\n        fn new() -\u003e MockMessenger {\n            MockMessenger {\n                sent_messages: RefCell::new(vec![]),\n            }\n        }\n    }\n\n    impl Messenger for MockMessenger {\n        fn send(\u0026self, message: \u0026str) {\n            self.sent_messages.borrow_mut().push(String::from(message));\n        }\n    }\n\n    #[test]\n    fn it_sends_an_over_75_percent_warning_message() {\n        // --snip--\n\n        assert_eq!(mock_messenger.sent_messages.borrow().len(), 1);\n    }\n}\n```\n\u003e The sent_messages field is now of type `RefCell\u003cVec\u003cString\u003e\u003e` instead of `Vec\u003cString\u003e`. In the new function, we create a new `RefCell\u003cVec\u003cString\u003e\u003e` instance around the empty vector.\n\n### Keeping Track of Borrows at Runtime with RefCell\u003cT\u003e\nWhen creating immutable and mutable references, we use the `\u0026` and `\u0026mut` syntax, respectively. With `RefCell\u003cT\u003e`, we use the borrow and borrow_mut methods, which are part of the safe API that belongs to `RefCell\u003cT\u003e`.\n\nIf we try to violate these rules, rather than getting a compiler error as we would with references, the implementation of RefCell\u003cT\u003e will panic at runtime.\n```rust\n    impl Messenger for MockMessenger {\n        fn send(\u0026self, message: \u0026str) {\n            let mut one_borrow = self.sent_messages.borrow_mut();\n            let mut two_borrow = self.sent_messages.borrow_mut();\n\n            one_borrow.push(String::from(message));\n            two_borrow.push(String::from(message));\n        }\n    }\n```\n\u003e We create a variable one_borrow for the RefMut\u003cT\u003e smart pointer returned from borrow_mut. Then we create another mutable borrow in the same way in the variable two_borrow. This makes two mutable references in the same scope, which isn’t allowed. \n\n\nChoosing to catch borrowing errors at runtime rather than compile time, as we’ve done here, means you’d potentially be finding mistakes in your code later in the development process: possibly not until your code was deployed to production. Also, your code would incur a small runtime performance penalty as a result of keeping track of the borrows at runtime rather than compile time. However, using RefCell\u003cT\u003e makes it possible to write a mock object that can modify itself to keep track of the messages it has seen while you’re using it in a context where only immutable values are allowed.\n\n### Having Multiple Owners of Mutable Data by Combining Rc\u003cT\u003e and RefCell\u003cT\u003e\nA common way to use `RefCell\u003cT\u003e` is in combination with `Rc\u003cT\u003e`.\n```rust\n#[derive(Debug)]\nenum List {\n    Cons(Rc\u003cRefCell\u003ci32\u003e\u003e, Rc\u003cList\u003e),\n    Nil,\n}\n\nuse crate::List::{Cons, Nil};\nuse std::cell::RefCell;\nuse std::rc::Rc;\n\nfn main() {\n    let value = Rc::new(RefCell::new(5));\n\n    let a = Rc::new(Cons(Rc::clone(\u0026value), Rc::new(Nil)));\n\n    let b = Cons(Rc::new(RefCell::new(3)), Rc::clone(\u0026a));\n    let c = Cons(Rc::new(RefCell::new(4)), Rc::clone(\u0026a));\n\n    *value.borrow_mut() += 10; // change inner value\n\n    println!(\"a after = {:?}\", a); // 15 not 5\n    println!(\"b after = {:?}\", b); // 15\n    println!(\"c after = {:?}\", c); // 15\n}\n```\n\u003e We create a value that is an instance of `Rc\u003cRefCell\u003ci32\u003e\u003e` and store it in a variable named value so we can access it directly later. \n\n## Reference Cycles Can Leak Memory\nRust’s memory safety guarantees make it difficult, but not impossible, to accidentally create memory that is never cleaned up (known as a memory leak).\n\n### Creating a Reference Cycle\nLet’s look at how a reference cycle might happen and how to prevent it, starting with the definition of the List `enum` and a `tail` method\n```rust\nuse crate::List::{Cons, Nil};\nuse std::cell::RefCell;\nuse std::rc::Rc;\n\n#[derive(Debug)]\nenum List {\n    Cons(i32, RefCell\u003cRc\u003cList\u003e\u003e),\n    Nil,\n}\n\nimpl List {\n    fn tail(\u0026self) -\u003e Option\u003c\u0026RefCell\u003cRc\u003cList\u003e\u003e\u003e {\n        match self {\n            Cons(_, item) =\u003e Some(item),\n            Nil =\u003e None,\n        }\n    }\n}\n\nfn main() {}\n```\n\nadding a main function that uses the definitions\n```rust\nfn main() {\n    let a = Rc::new(Cons(5, RefCell::new(Rc::new(Nil)))); // instance with 5\n\n    println!(\"a initial rc count = {}\", Rc::strong_count(\u0026a));\n    println!(\"a next item = {:?}\", a.tail());\n\n    let b = Rc::new(Cons(10, RefCell::new(Rc::clone(\u0026a)))); // points to a\n\n    println!(\"a rc count after b creation = {}\", Rc::strong_count(\u0026a));\n    println!(\"b initial rc count = {}\", Rc::strong_count(\u0026b));\n    println!(\"b next item = {:?}\", b.tail());\n\n    if let Some(link) = a.tail() { // change a to point to b -\u003e cycle\n        *link.borrow_mut() = Rc::clone(\u0026b);\n    }\n\n    println!(\"b rc count after changing a = {}\", Rc::strong_count(\u0026b));\n    println!(\"a rc count after changing a = {}\", Rc::strong_count(\u0026a));\n\n    // Uncomment the next line to see that we have a cycle;\n    // it will overflow the stack\n    // println!(\"a next item = {:?}\", a.tail());\n}\n```\n\u003e The reference count of the `Rc\u003cList\u003e` instances in both a and b are 2 after we change the list in `a` to point to `b`. At the end of main, Rust drops the variable `b`, which decreases the reference count of the `b` `Rc\u003cList\u003e` instance from 2 to 1. The memory that `Rc\u003cList\u003e` has on the heap won’t be dropped at this point, because its reference count is 1, not 0.\n\n### Preventing Reference Cycles: Turning an Rc\u003cT\u003e into a Weak\u003cT\u003e\nYou can also create a weak reference to the value within an `Rc\u003cT\u003e` instance by calling `Rc::downgrade` and passing a reference to the `Rc\u003cT\u003e`.\n\nCreating a Tree Data Structure: a Node with Child Nodes\n```rust\nuse std::cell::RefCell;\nuse std::rc::Rc;\n\n#[derive(Debug)]\nstruct Node {\n    value: i32,\n    children: RefCell\u003cVec\u003cRc\u003cNode\u003e\u003e\u003e,\n}\n```\n\u003e We want a Node to own its children, and we want to share that ownership with variables so we can access each Node in the tree directly.\n\nWe’ll use our struct definition and create one Node instance named leaf with the value 3 and no children, and another instance named branch with the value 5 and leaf as one of its children, \n```rust\nfn main() {\n    let leaf = Rc::new(Node {\n        value: 3,\n        children: RefCell::new(vec![]),\n    });\n\n    let branch = Rc::new(Node {\n        value: 5,\n        children: RefCell::new(vec![Rc::clone(\u0026leaf)]),\n    });\n}\n```\n\u003e We clone the Rc\u003cNode\u003e in leaf and store that in branch, meaning the Node in leaf now has two owners: leaf and branch. \n\nAdding a Reference from a Child to Its Parent\n```rust\nuse std::cell::RefCell;\nuse std::rc::{Rc, Weak};\n\n#[derive(Debug)]\nstruct Node {\n    value: i32,\n    parent: RefCell\u003cWeak\u003cNode\u003e\u003e, // use weak instead of RC\u003cT\u003e\n    children: RefCell\u003cVec\u003cRc\u003cNode\u003e\u003e\u003e,\n}\n```\n\u003e To make the child node aware of its parent, we need to add a parent field to our Node struct definition. \n\nA node will be able to refer to its parent node but doesn’t own its parent.\n```rust\nfn main() {\n    let leaf = Rc::new(Node {\n        value: 3,\n        parent: RefCell::new(Weak::new()), // empty ref\n        children: RefCell::new(vec![]),\n    });\n\n    println!(\"leaf parent = {:?}\", leaf.parent.borrow().upgrade());\n\n    let branch = Rc::new(Node {\n        value: 5,\n        parent: RefCell::new(Weak::new()),\n        children: RefCell::new(vec![Rc::clone(\u0026leaf)]),\n    });\n\n    *leaf.parent.borrow_mut() = Rc::downgrade(\u0026branch);\n\n    println!(\"leaf parent = {:?}\", leaf.parent.borrow().upgrade());\n}\n```\n\u003e When we create the branch node, it will also have a new Weak\u003cNode\u003e reference in the parent field, because branch doesn’t have a parent node. We still have leaf as one of the children of branch. Once we have the Node instance in branch, we can modify leaf to give it a Weak\u003cNode\u003e reference to its parent. We use the borrow_mut method on the RefCell\u003cWeak\u003cNode\u003e\u003e in the parent field of leaf, and then we use the Rc::downgrade function to create a Weak\u003cNode\u003e reference to branch from the Rc\u003cNode\u003e in branch.\n\nWhen we print the parent of leaf again, this time we’ll get a Some variant holding branch: now leaf can access its parent! When we print leaf, we also avoid the cycle that eventually ended in a stack overflow\n```rust\nleaf parent = Some(Node { value: 5, parent: RefCell { value: (Weak) },\nchildren: RefCell { value: [Node { value: 3, parent: RefCell { value: (Weak) },\nchildren: RefCell { value: [] } }] } })\n```\n\n### Visualizing Changes to strong_count and weak_count\nLet’s look at how the strong_count and weak_count values of the Rc\u003cNode\u003e instances change by creating a new inner scope and moving the creation of branch into that scope.\n```rust\nuse std::cell::RefCell;\nuse std::rc::{Rc, Weak};\n\n#[derive(Debug)]\nstruct Node {\n    value: i32,\n    parent: RefCell\u003cWeak\u003cNode\u003e\u003e,\n    children: RefCell\u003cVec\u003cRc\u003cNode\u003e\u003e\u003e,\n}\n\nfn main() {\n    let leaf = Rc::new(Node {\n        value: 3,\n        parent: RefCell::new(Weak::new()),\n        children: RefCell::new(vec![]),\n    });\n\n    println!(\n        \"leaf strong = {}, weak = {}\",\n        Rc::strong_count(\u0026leaf),\n        Rc::weak_count(\u0026leaf),\n    );\n\n    {\n        let branch = Rc::new(Node {\n            value: 5,\n            parent: RefCell::new(Weak::new()),\n            children: RefCell::new(vec![Rc::clone(\u0026leaf)]),\n        });\n\n        *leaf.parent.borrow_mut() = Rc::downgrade(\u0026branch);\n\n        println!(\n            \"branch strong = {}, weak = {}\",\n            Rc::strong_count(\u0026branch),\n            Rc::weak_count(\u0026branch),\n        );\n\n        println!(\n            \"leaf strong = {}, weak = {}\",\n            Rc::strong_count(\u0026leaf),\n            Rc::weak_count(\u0026leaf),\n        );\n    }\n\n    println!(\"leaf parent = {:?}\", leaf.parent.borrow().upgrade());\n    println!(\n        \"leaf strong = {}, weak = {}\",\n        Rc::strong_count(\u0026leaf),\n        Rc::weak_count(\u0026leaf),\n    );\n}\n```\n\u003e After leaf is created, its Rc\u003cNode\u003e has a strong count of 1 and a weak count of 0. In the inner scope, we create branch and associate it with leaf, at which point when we print the counts, the Rc\u003cNode\u003e in branch will have a strong count of 1 and a weak count of 1 (for leaf.parent pointing to branch with a Weak\u003cNode\u003e). When we print the counts in leaf, we’ll see it will have a strong count of 2, because branch now has a clone of the Rc\u003cNode\u003e of leaf stored in branch.children, but will still have a weak count of 0.\n\u003e When the inner scope ends, branch goes out of scope and the strong count of the Rc\u003cNode\u003e decreases to 0, so its Node is dropped. The weak count of 1 from leaf.parent has no bearing on whether or not Node is dropped, so we don’t get any memory leaks!\n\nAll of the logic that manages the counts and value dropping is built into Rc\u003cT\u003e and Weak\u003cT\u003e and their implementations of the Drop trait. By specifying that the relationship from a child to its parent should be a Weak\u003cT\u003e reference in the definition of Node, you’re able to have parent nodes point to child nodes and vice versa without creating a reference cycle and memory leaks.\n\n## Summary\nThis chapter covered how to use smart pointers to make different guarantees and trade-offs from those Rust makes by default with regular references. The `Box\u003cT\u003e` type has a known size and points to data allocated on the heap. The `Rc\u003cT\u003e` type keeps track of the number of references to data on the heap so that data can have multiple owners. The `RefCell\u003cT\u003e` type with its interior mutability gives us a type that we can use when we need an immutable type but need to change an inner value of that type; it also enforces the borrowing rules at runtime instead of at compile time.\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fzakharb%2Frustguide","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fzakharb%2Frustguide","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fzakharb%2Frustguide/lists"}