Rust for the Novice Programmer/Loops and Iteration

Loops and iteration

edit

Let's say we wanted to go through all the numbers from 1 to 100 and print out all the ones which are divisible by 6. How would we do this? Well, we could write a function checking if a number is divisible by 6 so let's do that first. By separating out the things we need to do we can deal with the problem one step at a time, which makes it easier to reason about. So first let's write the shell of the function:

 fn is_divisible_six(input: i32) -> bool {
     //to do
 }

We use the comment here to indicate we're going to fill out the inside of the function. This won't compile currently since the function must return a boolean value of either true or false and at the moment it returns nothing.
How do we check if a number is divisible by six? A quick refresher, being divisible by 6 means if it is divided by 6, the result will be a whole number. However, the input type is i32 so dividing by 6 will always return a whole number since it is doing integer division. So how do we proceed? One way would be to constantly subtract 6 from the number until we get to a number less than 6. If that number is 0, it means the number is divisible by 6, if not then it is not. Then the question is how do we express the 'constantly' 'until' in that logic. The answer is the while loop. A while loop while continually run whatever is inside the {} braces as long as the boolean value(called the condition) is true.

 fn is_divisible_six(input: i32) -> bool {
     let mut number = input;
     while number >= 6 {
         number -= 6;
     }
     if number == 0 {
          return true;
     } else {
          return false;
     }
 }

This is a direct translation of the steps earlier into code. Note that we could write it as 6 < number which is the same but by convention we normally put the variable on the left of conditions since it is more natural to read and understand.
What we are doing here is finding the remainder of input. This is quite a common thing, so there is a built-in way to do this, using the percent sign %. So a % b gets the remainder of a divided by b. Therefore, it is much simpler to write the function as this:

 fn is_divisible_six(input: i32) -> bool {
     let remainder = input % 6;
     if remainder == 0 {
          return true;
     } else {
          return false;
     }
 }

We can simplify this further since remainder == 0 is already a boolean value that corresponds to what we want to return, so we can do:

 fn is_divisible_six(input: i32) -> bool {
     let remainder = input % 6;
     return remainder == 0;
 }

This is much better. The morale of the remainder operator is if you're doing something quite common, there's probably a simple way to do it and the best way to find these ways is generally to search.

Back to the original thing, which was to go through all the numbers from 1 to 100 and print them if they're divisible by 6. Now we can do this using a while loop, we just have to set a number to 1, then keep going through the loop while the number is less than or equal to 100.

 fn main() {
     let mut number = 1;
     while number <= 100 {
          if is_divisible_six(number) {
              println!("{}", number);
          }
     }
 }

This works, but there is a built in easy way to iterate through numbers. These are called for loops, and we would rewrite the above as following:

 fn main() {
     for number in 1..101 {
         if is_divisible_six(number) {
             println!("{}", number);
         }
     }
 }

This does the same result as the while loop above but is a little cleaner. The 1..101 is called a range and it ranges from 1 to 100. The reason it has to be 101 on the right side of the .. is that it is non inclusive, meaning it doesn't include the last number. The reason for this will be seen later. We can use an inclusive range with ..= so 1..=100 would yield the same result. The 'for number in' indicates a variable called number that stores the value as the for loop goes through the values in the range. A for loop can iterate through anything that is an 'iterator' which will be explained soon.

Next: Arrays and Vectors