part02.rs lines shortened
[rust-101.git] / src / part10.rs
index 696988913c9dd7d79851016b35f7819708562f7e..0c90369c47145464411d557acc2f44fcb74d6788 100644 (file)
@@ -9,10 +9,10 @@ use part05::BigInt;
 //@ our function. In Rust, a natural first attempt to express this is to have a trait for it.
 
 // So, let us define a trait that demands that the type provides some method `do_action` on digits.
 //@ our function. In Rust, a natural first attempt to express this is to have a trait for it.
 
 // So, let us define a trait that demands that the type provides some method `do_action` on digits.
-//@ This immediately raises the question: How do we pass `self` to that function? Owned, shared borrow,
-//@ or mutable borrow? The typical strategy to answer this question is to use the strongest
+//@ This immediately raises the question: How do we pass `self` to that function? Owned, shared reference,
+//@ or mutable reference? The typical strategy to answer this question is to use the strongest
 //@ type that still works. Certainly, passing `self` in owned form does not work: Then the function
 //@ type that still works. Certainly, passing `self` in owned form does not work: Then the function
-//@ would consume `self`, and we could not call it again, on the second digit. So let's go with a mutable borrow.
+//@ would consume `self`, and we could not call it again, on the second digit. So let's go with a mutable reference.
 trait Action {
     fn do_action(&mut self, digit: u64);
 }
 trait Action {
     fn do_action(&mut self, digit: u64);
 }
@@ -21,7 +21,7 @@ trait Action {
 impl BigInt {
     fn act_v1<A: Action>(&self, mut a: A) {
         //@ Remember that the `mut` above is just an annotation to Rust, telling it that we're okay with `a` being mutated.
 impl BigInt {
     fn act_v1<A: Action>(&self, mut a: A) {
         //@ Remember that the `mut` above is just an annotation to Rust, telling it that we're okay with `a` being mutated.
-        //@ Calling `do_action` on `a` takes a mutable borrow, so mutation could indeed happen.
+        //@ Calling `do_action` on `a` takes a mutable reference, so mutation could indeed happen.
         for digit in self {
             a.do_action(digit);                                     /*@*/
         }
         for digit in self {
             a.do_action(digit);                                     /*@*/
         }
@@ -62,7 +62,7 @@ pub fn main() {
 //@ In general, this is called a *closure*. Closures take some arguments and produce a result, and they have an *environment*
 //@ they can use, which corresponds to the type `PrintWithString` (or any other type implementing `Action`). Again we have the
 //@ choice of passing this environment in owned or borrowed form, so there are three traits for closures in Rust: `Fn`-closures
 //@ In general, this is called a *closure*. Closures take some arguments and produce a result, and they have an *environment*
 //@ they can use, which corresponds to the type `PrintWithString` (or any other type implementing `Action`). Again we have the
 //@ choice of passing this environment in owned or borrowed form, so there are three traits for closures in Rust: `Fn`-closures
-//@ get a shared borrow, `FnMut`-closures get a mutable borrow, and `FnOnce`-closures consume their environment (and can hence
+//@ get a shared reference, `FnMut`-closures get a mutable reference, and `FnOnce`-closures consume their environment (and can hence
 //@ be called only once). The syntax for a closure trait which takes arguments of type `T1`, `T2`, ... and returns something
 //@ of type `U` is `Fn(T1, T2, ...) -> U`.
 
 //@ be called only once). The syntax for a closure trait which takes arguments of type `T1`, `T2`, ... and returns something
 //@ of type `U` is `Fn(T1, T2, ...) -> U`.
 
@@ -81,7 +81,7 @@ impl BigInt {
 pub fn print_with_prefix(b: &BigInt, prefix: String) {
     //@ The syntax for closures is `|arg1, arg2, ...| code`. Notice that the closure can reference variables like `prefix` that it did not
     //@ take as argument - variables that happen to be present *outside* of the closure. We say that the closure *captures*
 pub fn print_with_prefix(b: &BigInt, prefix: String) {
     //@ The syntax for closures is `|arg1, arg2, ...| code`. Notice that the closure can reference variables like `prefix` that it did not
     //@ take as argument - variables that happen to be present *outside* of the closure. We say that the closure *captures*
-    //@ variables. Rust will now automatically create a type (like `PrintWithStruct`) for the environment of the closure
+    //@ variables. Rust will now automatically create a type (like `PrintWithString`) for the environment of the closure
     //@ with fields for every captured variable, implement the closure trait for this type such that the action performed
     //@ is given by the code of the closure, and finally it will instantiate the environment type here at the definition site
     //@ of the closure and fill it appropriately.
     //@ with fields for every captured variable, implement the closure trait for this type such that the action performed
     //@ is given by the code of the closure, and finally it will instantiate the environment type here at the definition site
     //@ of the closure and fill it appropriately.
@@ -94,11 +94,11 @@ pub fn print_with_prefix(b: &BigInt, prefix: String) {
 // For example, we can use that to count the digits as they are printed.
 pub fn print_and_count(b: &BigInt) {
     let mut count: usize = 0;
 // For example, we can use that to count the digits as they are printed.
 pub fn print_and_count(b: &BigInt) {
     let mut count: usize = 0;
-    //@ This time, the environment will contain a field of type `&mut usize`, that will be initialized with a mutable borrow of
+    //@ This time, the environment will contain a field of type `&mut usize`, that will be initialized with a mutable reference of
     //@ `count`. The closure, since it mutably borrows its environment, is able to access this field and mutate `count`
     //@ `count`. The closure, since it mutably borrows its environment, is able to access this field and mutate `count`
-    //@ through it. Once `act` returns, the closure is destroyed and the borrow of `count` ends. Because closures compile down
+    //@ through it. Once `act` returns, the closure is destroyed and `count` is no longer borrowed. Because closures compile down
     //@ to normal types, all the borrow checking continues to work as usually, and we cannot accidentally leak a closure somewhere
     //@ to normal types, all the borrow checking continues to work as usually, and we cannot accidentally leak a closure somewhere
-    //@ that still contains, in its environment, a borrow that has ended.
+    //@ that still contains, in its environment, a dead reference.
     b.act(|digit| { println!("{}: {}", count, digit); count = count +1; } );
     println!("There are {} digits", count);
 }
     b.act(|digit| { println!("{}: {}", count, digit); count = count +1; } );
     println!("There are {} digits", count);
 }
@@ -108,7 +108,7 @@ pub fn print_and_count(b: &BigInt) {
 //@ Rust provides a whole lot of methods on iterators that allow us to write pretty functional-style list manipulation.
 
 // Let's say we want to write a function that increments every entry of a `Vec` by some number, then looks for numbers larger than some threshold, and prints them.
 //@ Rust provides a whole lot of methods on iterators that allow us to write pretty functional-style list manipulation.
 
 // Let's say we want to write a function that increments every entry of a `Vec` by some number, then looks for numbers larger than some threshold, and prints them.
-fn inc_print_even(v: &Vec<i32>, offset: i32, threshold: i32) {
+fn inc_print_threshold(v: &Vec<i32>, offset: i32, threshold: i32) {
     //@ `map` takes a closure that is applied to every element of the iterator. `filter` removes elements
     //@ from the iterator that do not pass the test given by the closure.
     //@ 
     //@ `map` takes a closure that is applied to every element of the iterator. `filter` removes elements
     //@ from the iterator that do not pass the test given by the closure.
     //@ 
@@ -141,4 +141,4 @@ fn filter_vec_by_divisor(v: &Vec<i32>, divisor: i32) -> Vec<i32> {
 // product of those numbers that sit at odd positions? A function that checks whether a vector contains a certain number? Whether all numbers are
 // smaller than some threshold? Be creative!
 
 // product of those numbers that sit at odd positions? A function that checks whether a vector contains a certain number? Whether all numbers are
 // smaller than some threshold? Be creative!
 
-//@ [index](main.html) | [previous](part09.html) | [raw source](https://www.ralfj.de/git/rust-101.git/blob_plain/HEAD:/workspace/src/part10.rs) | [next](part11.html)
+//@ [index](main.html) | [previous](part09.html) | [raw source](workspace/src/part10.rs) | [next](part11.html)