Advertisement
Toumo

Rust by Example

Aug 4th, 2022 (edited)
1,189
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Rust 10.92 KB | Source Code | 0 0
  1. /*
  2. Rust by Example
  3. https://doc.rust-lang.org/stable/rust-by-example/
  4. Collection of solved activities from the Rust by Example book
  5. */
  6.  
  7. /*
  8. Questions
  9. 9.2.1. Capturing
  10. https://doc.rust-lang.org/stable/rust-by-example/fn/closures/capture.html
  11. https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=2bae19b86f57bd5a08f04645e48d6069
  12. */
  13.  
  14. ////////////////////////////////////////////////////////////////////////////////////////////////////////
  15.  
  16. /*
  17. 1.2. Formatted print
  18. https://doc.rust-lang.org/stable/rust-by-example/hello/print.html
  19. Print a float with a given precision println!("{pi:.N}")
  20. https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=98026c4b84e9a36bc8de3f3ff2ec6238
  21. */
  22. fn main() {
  23.     let pi = 3.141592; // round to third
  24.     println!("Pi is roughly {pi:.3}");
  25. }
  26.  
  27. ////////////////////////////////////////////////////////////////////////////////////////////////////////
  28.  
  29. /*
  30. 1.2.2. Display
  31. https://doc.rust-lang.org/stable/rust-by-example/hello/print/print_display.html
  32. Implement fmt::Display for custom struct
  33. https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=4535be35f1f50120faa302f7c9ec1b01
  34. */
  35. use std::fmt; // Import `fmt`
  36.  
  37. #[derive(Debug)]
  38. struct Complex {
  39.     real: f64,
  40.     imag: f64,
  41. }
  42.  
  43. // Implement `Display` for `Complex`
  44. impl fmt::Display for Complex {
  45.     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
  46.         write!(f, "{0} + {1}i", self.real, self.imag)
  47.     }
  48. }
  49.  
  50. fn main() {
  51.     let complex_num = Complex { real: 3.3, imag: 7.2};
  52.     println!("Display: {}", complex_num);
  53.     println!("Debug: {:?}", complex_num);
  54. }
  55.  
  56. ////////////////////////////////////////////////////////////////////////////////////////////////////////
  57.  
  58. /*
  59. 1.2.2.1. Testcase: List
  60. https://doc.rust-lang.org/stable/rust-by-example/hello/print/print_display/testcase_list.html
  61. Modify the implementation of fmt::Display for a list-like struct to display indexes next to values
  62. https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=b3ee1e88f382f65f45f4ff74f6dda5b1
  63. */
  64. use std::fmt; // Import the `fmt` module.
  65.  
  66. // Define a structure named `List` containing a `Vec`.
  67. struct List(Vec<i32>);
  68.  
  69. impl fmt::Display for List {
  70.     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
  71.         // Extract the value using tuple indexing,
  72.         // and create a reference to `vec`.
  73.         let vec = &self.0;
  74.  
  75.         write!(f, "[")?;
  76.  
  77.         // Iterate over `v` in `vec` while enumerating the iteration
  78.         // count in `count`.
  79.         for (count, v) in vec.iter().enumerate() {
  80.             // For every element except the first, add a comma.
  81.             // Use the ? operator to return on errors.
  82.             if count != 0 { write!(f, ", ")?; }
  83.             write!(f, "{0}: {1}", count, v)?;
  84.         }
  85.  
  86.         // Close the opened bracket and return a fmt::Result value.
  87.         write!(f, "]")
  88.     }
  89. }
  90.  
  91. fn main() {
  92.     let v = List(vec![1, 2, 3]);
  93.     println!("{}", v);
  94. }
  95.  
  96. ////////////////////////////////////////////////////////////////////////////////////////////////////////
  97.  
  98. /*
  99. 1.2.3. Formatting
  100. https://doc.rust-lang.org/stable/rust-by-example/hello/print/fmt.html
  101. Implement fmt::Display for the Color struct so that both the RGB tuple and hex representation are shown
  102. https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=0b5857134428e2d4824c1807a496ab71
  103. */
  104. use std::fmt::{self, Formatter, Display};
  105.  
  106. struct Color {
  107.     red: u8,
  108.     green: u8,
  109.     blue: u8,
  110. }
  111.  
  112. impl Display for Color {
  113.     // `f` is a buffer, and this method must write the formatted string into it
  114.     fn fmt(&self, f: &mut Formatter) -> fmt::Result {
  115.         // `write!` is like `format!`, but it will write the formatted string
  116.         // into a buffer (the first argument)
  117.         write!(f, "RGB ({0}, {1}, {2}) 0x{0:0>2X}{1:0>2X}{2:0>2X}", self.red, self.green, self.blue)
  118.     }
  119. }
  120.  
  121. fn main() {
  122.     for color in [
  123.         Color { red: 128, green: 255, blue: 90 },
  124.         Color { red: 0, green: 3, blue: 254 },
  125.         Color { red: 0, green: 0, blue: 0 },
  126.     ].iter() {
  127.         println!("{}", *color);
  128.     }
  129. }
  130.  
  131. ////////////////////////////////////////////////////////////////////////////////////////////////////////
  132.  
  133. /*
  134. 2.2. Tuples
  135. https://doc.rust-lang.org/stable/rust-by-example/primitives/tuples.html
  136. 1. Implement fmt::Display trait for the Matrix struct
  137. 2. Implement transpose() for the 2x2 matrices of the Matrix struct
  138. https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=72949ad5fd23f92da73f8a1e8f980ad3
  139. */
  140. use std::fmt;
  141.  
  142. // Tuples can be used as function arguments and as return values
  143. fn reverse(pair: (i32, bool)) -> (bool, i32) {
  144.     // `let` can be used to bind the members of a tuple to variables
  145.     let (integer, boolean) = pair;
  146.  
  147.     (boolean, integer)
  148. }
  149.  
  150. fn transpose(matrix: Matrix) -> Matrix {
  151.     Matrix(matrix.0, matrix.2, matrix.1, matrix.3) // 2
  152. }
  153.  
  154. // The following struct is for the activity.
  155. #[derive(Debug)]
  156. struct Matrix(f32, f32, f32, f32);
  157.  
  158. impl fmt::Display for Matrix {
  159.     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
  160.         write!(f, "({0} {1})\n({2} {3})", self.0, self.1, self.2, self.3) // Backslash is AltGr+' // 1
  161.     }
  162. }
  163.  
  164. fn main() {
  165.     // A tuple with a bunch of different types
  166.     let long_tuple = (1u8, 2u16, 3u32, 4u64,
  167.                       -1i8, -2i16, -3i32, -4i64,
  168.                       0.1f32, 0.2f64,
  169.                       'a', true);
  170.  
  171.     // Values can be extracted from the tuple using tuple indexing
  172.     println!("long tuple first value: {}", long_tuple.0);
  173.     println!("long tuple second value: {}", long_tuple.1);
  174.  
  175.     // Tuples can be tuple members
  176.     let tuple_of_tuples = ((1u8, 2u16, 2u32), (4u64, -1i8), -2i16);
  177.  
  178.     // Tuples are printable
  179.     println!("tuple of tuples: {:?}", tuple_of_tuples);
  180.    
  181.     // But long Tuples (more than 12 elements) cannot be printed
  182.     // let too_long_tuple = (1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13);
  183.     // println!("too long tuple: {:?}", too_long_tuple);
  184.     // TODO ^ Uncomment the above 2 lines to see the compiler error
  185.  
  186.     let pair = (1, true);
  187.     println!("pair is {:?}", pair);
  188.  
  189.     println!("the reversed pair is {:?}", reverse(pair));
  190.  
  191.     // To create one element tuples, the comma is required to tell them apart
  192.     // from a literal surrounded by parentheses
  193.     println!("one element tuple: {:?}", (5u32,));
  194.     println!("just an integer: {:?}", (5u32));
  195.  
  196.     //tuples can be destructured to create bindings
  197.     let tuple = (1, "hello", 4.5, true);
  198.  
  199.     let (a, b, c, d) = tuple;
  200.     println!("{:?}, {:?}, {:?}, {:?}", a, b, c, d);
  201.  
  202.     let matrix = Matrix(1.1, 1.2, 2.1, 2.2);
  203.     println!("{:?}", matrix);
  204.  
  205.     println!("Matrix:\n{}", matrix);
  206.     println!("Transpose:\n{}", transpose(matrix));
  207. }
  208.  
  209. ////////////////////////////////////////////////////////////////////////////////////////////////////////
  210.  
  211. /*
  212. 3.1. Structs
  213. https://doc.rust-lang.org/stable/rust-by-example/custom_types/structs.html
  214. 1. Implement rect_area() for Rectangle structs
  215. 2. Implement square() that from a Point and a float returns a Rectangle... that is a square
  216. https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=424032cd98d5f107d83aae52b6254be4
  217. */
  218. // Attributes to hide warnings for unused code and unused variables.
  219. #![allow(dead_code)]
  220. #![allow(unused_variables)]
  221.  
  222. #[derive(Debug)]
  223. struct Person {
  224.     name: String,
  225.     age: u8,
  226. }
  227.  
  228. // A unit struct
  229. struct Unit;
  230.  
  231. // A tuple struct
  232. struct Pair(i32, f32);
  233.  
  234. // A struct with two fields
  235. #[derive(Debug)]
  236. struct Point {
  237.     x: f32,
  238.     y: f32,
  239. }
  240.  
  241. // Structs can be reused as fields of another struct
  242. #[derive(Debug)]
  243. struct Rectangle {
  244.     // A rectangle can be specified by where the top left and bottom right
  245.     // corners are in space.
  246.     top_left: Point,
  247.     bottom_right: Point,
  248. }
  249.  
  250. fn rect_area(rect: &Rectangle) -> f32 {
  251.     let Rectangle {
  252.         top_left: Point { x: x1, y: y1 },
  253.         bottom_right: Point { x: x2, y: y2 } } = rect;
  254.  
  255.     ((x2-x1)*(y2-y1)).abs() // 1
  256. }
  257.  
  258. fn square(top_left_corner: Point, side_length: f32) -> Rectangle {
  259.     let Point { x: x1, y: y1 } = top_left_corner;
  260.     Rectangle {
  261.         top_left: Point { x: x1, y: y1 },
  262.         bottom_right: Point {
  263.             x: x1 + side_length,
  264.             y: y1 + side_length
  265.         }
  266.     } // 2
  267. }
  268.  
  269. fn main() {
  270.     // Create struct with field init shorthand
  271.     let name = String::from("Peter");
  272.     let age = 27;
  273.     let peter = Person { name, age };
  274.  
  275.     // Print debug struct
  276.     println!("{:?}", peter);
  277.  
  278.     // Instantiate a `Point`
  279.     let point: Point = Point { x: 10.3, y: 0.4 };
  280.  
  281.     // Access the fields of the point
  282.     println!("point coordinates: ({}, {})", point.x, point.y);
  283.  
  284.     // Make a new point by using struct update syntax to use the fields of our
  285.     // other one
  286.     let bottom_right = Point { x: 5.2, ..point };
  287.  
  288.     // `bottom_right.y` will be the same as `point.y` because we used that field
  289.     // from `point`
  290.     println!("second point: ({}, {})", bottom_right.x, bottom_right.y);
  291.  
  292.     // Destructure the point using a `let` binding
  293.     let Point { x: left_edge, y: top_edge } = point;
  294.  
  295.     let _rectangle = Rectangle {
  296.         // struct instantiation is an expression too
  297.         top_left: Point { x: left_edge, y: top_edge },
  298.         bottom_right: bottom_right,
  299.     };
  300.  
  301.     // Instantiate a unit struct
  302.     let _unit = Unit;
  303.  
  304.     // Instantiate a tuple struct
  305.     let pair = Pair(1, 0.1);
  306.  
  307.     // Access the fields of a tuple struct
  308.     println!("pair contains {:?} and {:?}", pair.0, pair.1);
  309.  
  310.     // Destructure a tuple struct
  311.     let Pair(integer, decimal) = pair;
  312.  
  313.     println!("pair contains {:?} and {:?}", integer, decimal);
  314.  
  315.     let rect1 = Rectangle {
  316.         top_left: Point { x: 0.0, y: 0.0 },
  317.         bottom_right: Point { x: 10.0, y: 15.0 },
  318.     };
  319.     let area = rect_area(&rect1);
  320.     println!("{:?} has area {}", rect1, area);
  321.     let square1 = square(point, 10.0);
  322.     let area = rect_area(&square1);
  323.     println!("{:?} has area {}", square1, area);
  324. }
  325.  
  326. ////////////////////////////////////////////////////////////////////////////////////////////////////////
  327.  
  328. /*
  329. 8.6. if let
  330. https://doc.rust-lang.org/stable/rust-by-example/flow_control/if_let.html
  331. Replace if .. == .. by if let .. = .. so that a conditional can be used on the non-parametrized enum var
  332. https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=6d19880b6cb267d64ce9c638e4b65f3f
  333. */
  334. // This enum purposely neither implements nor derives PartialEq.
  335. // That is why comparing Goo::Bar == a fails below.
  336. enum Goo {Bar}
  337.  
  338. fn main() {
  339.     let a = Goo::Bar;
  340.  
  341.     // Variable a matches Goo::Bar
  342.     if let Goo::Bar = a {
  343.         println!("a is goobar");
  344.     }
  345. }
  346.  
  347. ////////////////////////////////////////////////////////////////////////////////////////////////////////
  348.  
  349. /*
  350.  
  351. */
  352.  
  353. ////////////////////////////////////////////////////////////////////////////////////////////////////////
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement