2.8 Control Flow Constructs
Rust provides standard control flow structures, but with some differences compared to C, particularly regarding conditions and loops.
2.8.1 Conditional Execution with if
, else if
, and else
fn main() { let number = 6; if number % 4 == 0 { println!("Number is divisible by 4"); } else if number % 3 == 0 { println!("Number is divisible by 3"); } else if number % 2 == 0 { println!("Number is divisible by 2"); } else { println!("Number is not divisible by 4, 3, or 2"); } }
As in C, Rust uses %
for the modulo operation and ==
to test for equality.
- Conditions must evaluate to a
bool
. Unlike C, integers are not automatically treated as true (non-zero) or false (zero). - Parentheses
()
around the condition are not required. - Curly braces
{}
around the blocks are mandatory, even for single statements, preventing potential danglingelse
issues. if
is an expression in Rust, meaning it can return a value:fn main() { let condition = true; let number = if condition { 5 } else { 6 }; // `if` as an expression println!("The number is {}", number); }
2.8.2 Repetition: loop
, while
, and for
Rust offers three looping constructs:
-
loop
: Creates an infinite loop, typically exited usingbreak
.break
can also return a value from the loop.fn main() { let mut counter = 0; let result = loop { counter += 1; if counter == 10 { break counter * 2; // Exit loop and return counter * 2 } }; println!("The loop result is {}", result); // Prints 20 }
-
while
: Executes a block as long as a boolean condition remains true.fn main() { let mut number = 3; while number != 0 { println!("{}!", number); number -= 1; } println!("LIFTOFF!!!"); }
-
for
: Iterates over elements produced by an iterator. This is the most common and idiomatic loop in Rust. It’s fundamentally different from C’s typical index-basedfor
loop.fn main() { // Iterate over a range (0 to 4) for i in 0..5 { println!("The number is: {}", i); } // Iterate over elements of an array let a = [10, 20, 30, 40, 50]; // `.iter()` creates an iterator over references; inferred since Rust 2021 for element in a { // or explicitly `a.iter()` println!("The value is: {}", element); } }
There is no direct equivalent to C’s
for (int i = 0; i < N; ++i)
construct in Rust. Range-basedfor
loops or explicit iterator usage are preferred for safety and clarity. -
continue
: Skips the rest of the current iteration and proceeds to the next one, usable in all loop types.
2.8.3 Control Flow Comparisons with C
- Rust enforces
bool
conditions inif
andwhile
. C allows integer conditions (0 is false, non-zero is true). - Rust requires braces
{}
forif
/else
/while
/for
blocks. C allows omitting them for single statements, which can be error-prone. - Rust’s
for
loop is exclusively iterator-based. C’sfor
loop is a general structure with initialization, condition, and increment parts. - Rust prevents assignments within
if
conditions (e.g.,if x = y { ... }
is an error), avoiding a common C pitfall (if (x = y)
vs.if (x == y)
). - Rust has
match
, a powerful pattern-matching construct (covered later) that is often more versatile than C’sswitch
.